heads up notifications, v0.1

1. re-name intruder alerts to heads up notifications
2. use interrupt for the verb form, instead of intrude
3. new policy: no full screen, high priority, screen on, not locked or dreaming
4. controlled by global setting, with an observer
5. only content view for now, expandable is a todo

to turn it on:
  adb  shell settings put global heads_up_enabled 1
calendar notifications (not pop-up) work well.

Change-Id: I253418c217d0a5cf81dc2fa001f4bad90fafcce5
This commit is contained in:
Chris Wren
2013-06-28 16:54:01 -04:00
parent 38b2322567
commit 157026f820
10 changed files with 142 additions and 134 deletions

View File

@ -15,6 +15,7 @@
-->
<selector xmlns:android="http://schemas.android.com/apk/res/android"
android:exitFadeDuration="@android:integer/config_mediumAnimTime">
<item android:state_pressed="true" android:drawable="@drawable/intruder_bg_pressed" />
android:exitFadeDuration="@android:integer/config_mediumAnimTime">
<item android:state_pressed="true"
android:drawable="@drawable/heads_up_notification_bg_pressed" />
</selector>

View File

Before

Width:  |  Height:  |  Size: 272 B

After

Width:  |  Height:  |  Size: 272 B

View File

@ -19,7 +19,7 @@
-->
<!-- android:background="@drawable/status_bar_closed_default_background" -->
<com.android.systemui.statusbar.policy.IntruderAlertView
<com.android.systemui.statusbar.policy.HeadsUpNotificationView
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_height="wrap_content"
android:layout_width="match_parent"
@ -29,12 +29,6 @@
android:layout_height="wrap_content"
android:layout_width="match_parent"
android:id="@+id/contentHolder"
android:background="@drawable/intruder_window_bg"
android:background="@drawable/heads_up_window_bg"
/>
<!-- <ImageView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:src="@drawable/title_bar_shadow"
android:scaleType="fitXY"
/> -->
</com.android.systemui.statusbar.policy.IntruderAlertView>
</com.android.systemui.statusbar.policy.HeadsUpNotificationView>

View File

@ -27,7 +27,7 @@
<color name="notification_list_shadow_top">#80000000</color>
<drawable name="recents_callout_line">#99ffffff</drawable>
<drawable name="notification_item_background_legacy_color">#ffaaaaaa</drawable>
<drawable name="intruder_bg_pressed">#ff33B5E5</drawable>
<drawable name="heads_up_notification_bg_pressed">#ff33B5E5</drawable>
<drawable name="notification_header_bg">#FF000000</drawable>
<color name="notification_panel_scrim_color">#B0000000</color>
</resources>

View File

@ -34,7 +34,7 @@
<item name="android:wallpaperIntraOpenExitAnimation">@anim/wallpaper_recents_launch_from_launcher_exit</item>
</style>
<style name="TextAppearance.StatusBar.IntruderAlert"
<style name="TextAppearance.StatusBar.HeadsUp"
parent="@*android:style/TextAppearance.StatusBar">
</style>
@ -154,9 +154,9 @@
<style name="Animation.StatusBar">
</style>
<style name="Animation.StatusBar.IntruderAlert">
<item name="android:windowEnterAnimation">@anim/priority_alert_enter</item>
<item name="android:windowExitAnimation">@anim/priority_alert_exit</item>
<style name="Animation.StatusBar.HeadsUp">
<item name="android:windowEnterAnimation">@anim/heads_up_enter</item>
<item name="android:windowExitAnimation">@anim/heads_up_exit</item>
</style>
<style name="TextAppearance.StatusBar.PhoneTicker"

View File

@ -35,10 +35,13 @@ import android.os.Build;
import android.os.Handler;
import android.os.IBinder;
import android.os.Message;
import android.os.PowerManager;
import android.os.RemoteException;
import android.os.ServiceManager;
import android.os.UserHandle;
import android.provider.Settings;
import android.service.dreams.DreamService;
import android.service.dreams.IDreamManager;
import android.service.notification.StatusBarNotification;
import android.text.TextUtils;
import android.util.Log;
@ -83,16 +86,19 @@ public abstract class BaseStatusBar extends SystemUI implements
protected static final int MSG_CANCEL_PRELOAD_RECENT_APPS = 1023;
protected static final int MSG_OPEN_SEARCH_PANEL = 1024;
protected static final int MSG_CLOSE_SEARCH_PANEL = 1025;
protected static final int MSG_SHOW_INTRUDER = 1026;
protected static final int MSG_HIDE_INTRUDER = 1027;
protected static final int MSG_SHOW_HEADS_UP = 1026;
protected static final int MSG_HIDE_HEADS_UP = 1027;
protected static final boolean ENABLE_INTRUDERS = false;
protected static final boolean ENABLE_HEADS_UP = true;
// scores above this threshold should be displayed in heads up mode.
private static final int INTERRUPTION_THRESHOLD = 10;
// Should match the value in PhoneWindowManager
public static final String SYSTEM_DIALOG_REASON_RECENT_APPS = "recentapps";
public static final int EXPANDED_LEAVE_ALONE = -10000;
public static final int EXPANDED_FULL_OPEN = -10001;
private static final String SETTING_HEADS_UP = "heads_up_enabled";
protected CommandQueue mCommandQueue;
protected IStatusBarService mBarService;
@ -102,7 +108,7 @@ public abstract class BaseStatusBar extends SystemUI implements
protected NotificationData mNotificationData = new NotificationData();
protected NotificationRowLayout mPile;
protected StatusBarNotification mCurrentlyIntrudingNotification;
protected StatusBarNotification mCurrentlyInterruptingNotification;
// used to notify status bar for suppressing notification LED
protected boolean mPanelSlightlyVisible;
@ -116,6 +122,11 @@ public abstract class BaseStatusBar extends SystemUI implements
protected int mLayoutDirection;
private Locale mLocale;
protected boolean mUseHeadsUp = true;
protected IDreamManager mDreamManager;
KeyguardManager mKeyguardManager;
PowerManager mPowerManager;
// UI-specific methods
@ -155,6 +166,19 @@ public abstract class BaseStatusBar extends SystemUI implements
}
};
final private ContentObserver mHeadsUpObserver = new ContentObserver(mHandler) {
@Override
public void onChange(boolean selfChange) {
mUseHeadsUp = ENABLE_HEADS_UP && 0 != Settings.Global.getInt(
mContext.getContentResolver(), SETTING_HEADS_UP, 0);
Log.d(TAG, "heads up is " + (mUseHeadsUp ? "enabled" : "disabled"));
if (!mUseHeadsUp) {
Log.d(TAG, "dismissing any existing heads up notification on disable event");
mHandler.sendEmptyMessage(MSG_HIDE_HEADS_UP);
}
}
};
private RemoteViews.OnClickHandler mOnClickHandler = new RemoteViews.OnClickHandler() {
@Override
public boolean onClickHandler(View view, PendingIntent pendingIntent, Intent fillInIntent) {
@ -204,11 +228,21 @@ public abstract class BaseStatusBar extends SystemUI implements
mWindowManagerService = WindowManagerGlobal.getWindowManagerService();
mDisplay = mWindowManager.getDefaultDisplay();
mDreamManager = IDreamManager.Stub.asInterface(
ServiceManager.checkService(DreamService.DREAM_SERVICE));
mKeyguardManager = (KeyguardManager) mContext.getSystemService(Context.KEYGUARD_SERVICE);
mPowerManager = (PowerManager) mContext.getSystemService(Context.POWER_SERVICE);
mProvisioningObserver.onChange(false); // set up
mContext.getContentResolver().registerContentObserver(
Settings.Global.getUriFor(Settings.Global.DEVICE_PROVISIONED), true,
mProvisioningObserver);
mHeadsUpObserver.onChange(false); // set up
mContext.getContentResolver().registerContentObserver(
Settings.Global.getUriFor(SETTING_HEADS_UP), true,
mHeadsUpObserver);
mBarService = IStatusBarService.Stub.asInterface(
ServiceManager.getService(Context.STATUS_BAR_SERVICE));
@ -398,7 +432,7 @@ public abstract class BaseStatusBar extends SystemUI implements
}
}
public void dismissIntruder() {
public void dismissHeadsUp() {
// pass
}
@ -677,13 +711,13 @@ public abstract class BaseStatusBar extends SystemUI implements
return new NotificationClicker(intent, pkg, tag, id);
}
private class NotificationClicker implements View.OnClickListener {
protected class NotificationClicker implements View.OnClickListener {
private PendingIntent mIntent;
private String mPkg;
private String mTag;
private int mId;
NotificationClicker(PendingIntent intent, String pkg, String tag, int id) {
public NotificationClicker(PendingIntent intent, String pkg, String tag, int id) {
mIntent = intent;
mPkg = pkg;
mTag = tag;
@ -730,9 +764,6 @@ public abstract class BaseStatusBar extends SystemUI implements
// close the shade if it was open
animateCollapsePanels(CommandQueue.FLAG_EXCLUDE_NONE);
visibilityChanged(false);
// If this click was on the intruder alert, hide that instead
// mHandler.sendEmptyMessage(MSG_HIDE_INTRUDER);
}
}
/**
@ -997,18 +1028,30 @@ public abstract class BaseStatusBar extends SystemUI implements
setAreThereNotifications();
updateExpandedViewPos(EXPANDED_LEAVE_ALONE);
// See if we need to update the intruder.
if (ENABLE_INTRUDERS && oldNotification == mCurrentlyIntrudingNotification) {
if (DEBUG) Log.d(TAG, "updating the current intruder:" + notification);
// See if we need to update the heads up.
if (ENABLE_HEADS_UP && oldNotification == mCurrentlyInterruptingNotification) {
if (DEBUG) Log.d(TAG, "updating the current heads up:" + notification);
// XXX: this is a hack for Alarms. The real implementation will need to *update*
// the intruder.
if (notification.getNotification().fullScreenIntent == null) { // TODO(dsandler): consistent logic with add()
if (DEBUG) Log.d(TAG, "no longer intrudes!");
mHandler.sendEmptyMessage(MSG_HIDE_INTRUDER);
// the heads up.
if (!shouldInterrupt(notification)) {
if (DEBUG) Log.d(TAG, "no longer interrupts!");
mHandler.sendEmptyMessage(MSG_HIDE_HEADS_UP);
}
}
}
protected boolean shouldInterrupt(StatusBarNotification notification) {
boolean interrupt = notification.getNotification().fullScreenIntent == null
&& notification.getScore() >= INTERRUPTION_THRESHOLD
&& mPowerManager.isScreenOn() && !mKeyguardManager.isKeyguardLocked();
try {
interrupt = interrupt && !mDreamManager.isDreaming();
} catch (RemoteException e) {
Log.d(TAG, "failed to query dream manager", e);
}
return interrupt;
}
// Q: What kinds of notifications should show during setup?
// A: Almost none! Only things coming from the system (package is "android") that also
// have special "kind" tags marking them as relevant for setup (see below).

View File

@ -45,12 +45,9 @@ import android.os.Handler;
import android.os.IBinder;
import android.os.Message;
import android.os.RemoteException;
import android.os.ServiceManager;
import android.os.SystemClock;
import android.os.UserHandle;
import android.provider.Settings;
import android.service.dreams.DreamService;
import android.service.dreams.IDreamManager;
import android.service.notification.StatusBarNotification;
import android.util.DisplayMetrics;
import android.util.EventLog;
@ -76,7 +73,6 @@ import android.widget.LinearLayout;
import android.widget.ScrollView;
import android.widget.TextView;
import android.widget.Toast;
import com.android.internal.statusbar.StatusBarIcon;
import com.android.systemui.EventLogTags;
import com.android.systemui.R;
@ -90,7 +86,7 @@ import com.android.systemui.statusbar.StatusBarIconView;
import com.android.systemui.statusbar.policy.BatteryController;
import com.android.systemui.statusbar.policy.BluetoothController;
import com.android.systemui.statusbar.policy.DateView;
import com.android.systemui.statusbar.policy.IntruderAlertView;
import com.android.systemui.statusbar.policy.HeadsUpNotificationView;
import com.android.systemui.statusbar.policy.LocationController;
import com.android.systemui.statusbar.policy.NetworkController;
import com.android.systemui.statusbar.policy.NotificationRowLayout;
@ -127,7 +123,7 @@ public class PhoneStatusBar extends BaseStatusBar {
// 1020-1030 reserved for BaseStatusBar
// will likely move to a resource or other tunable param at some point
private static final int INTRUDER_ALERT_DECAY_MS = 0; // disabled, was 10000;
private static final int HEADS_UP_DECAY_MS = 0; // disabled, was 10000;
private static final boolean CLOSE_PANEL_WHEN_EMPTIED = true;
@ -169,8 +165,6 @@ public class PhoneStatusBar extends BaseStatusBar {
Display mDisplay;
Point mCurrentDisplaySize = new Point();
IDreamManager mDreamManager;
StatusBarWindowView mStatusBarWindow;
PhoneStatusBarView mStatusBarView;
@ -230,8 +224,8 @@ public class PhoneStatusBar extends BaseStatusBar {
// the date view
DateView mDateView;
// for immersive activities
private IntruderAlertView mIntruderAlertView;
// for heads up notifications
private HeadsUpNotificationView mHeadsUpNotificationView;
// on-screen navigation buttons
private NavigationBarView mNavigationBarView = null;
@ -358,14 +352,11 @@ public class PhoneStatusBar extends BaseStatusBar {
.getDefaultDisplay();
mDisplay.getSize(mCurrentDisplaySize);
mDreamManager = IDreamManager.Stub.asInterface(
ServiceManager.checkService(DreamService.DREAM_SERVICE));
super.start(); // calls createAndAddWindows()
addNavigationBar();
if (ENABLE_INTRUDERS) addIntruderView();
if (ENABLE_HEADS_UP) addHeadsUpView();
// Lastly, call to the icon policy to install/update all the icons.
mIconPolicy = new PhoneStatusBarPolicy(mContext);
@ -424,10 +415,11 @@ public class PhoneStatusBar extends BaseStatusBar {
mNotificationPanel.setBackground(new FastColorDrawable(context.getResources().getColor(
R.color.notification_panel_solid_background)));
}
if (ENABLE_INTRUDERS) {
mIntruderAlertView = (IntruderAlertView) View.inflate(context, R.layout.intruder_alert, null);
mIntruderAlertView.setVisibility(View.GONE);
mIntruderAlertView.setBar(this);
if (ENABLE_HEADS_UP) {
mHeadsUpNotificationView =
(HeadsUpNotificationView) View.inflate(context, R.layout.heads_up, null);
mHeadsUpNotificationView.setVisibility(View.GONE);
mHeadsUpNotificationView.setBar(this);
}
if (MULTIUSER_DEBUG) {
mNotificationPanelDebugText = (TextView) mNotificationPanel.findViewById(R.id.header_debug_info);
@ -833,7 +825,7 @@ public class PhoneStatusBar extends BaseStatusBar {
return lp;
}
private void addIntruderView() {
private void addHeadsUpView() {
WindowManager.LayoutParams lp = new WindowManager.LayoutParams(
ViewGroup.LayoutParams.MATCH_PARENT,
ViewGroup.LayoutParams.WRAP_CONTENT,
@ -847,11 +839,11 @@ public class PhoneStatusBar extends BaseStatusBar {
PixelFormat.TRANSLUCENT);
lp.gravity = Gravity.TOP | Gravity.FILL_HORIZONTAL;
//lp.y += height * 1.5; // FIXME
lp.setTitle("IntruderAlert");
lp.setTitle("Heads Up");
lp.packageName = mContext.getPackageName();
lp.windowAnimations = R.style.Animation_StatusBar_IntruderAlert;
lp.windowAnimations = R.style.Animation_StatusBar_HeadsUp;
mWindowManager.addView(mIntruderAlertView, lp);
mWindowManager.addView(mHeadsUpNotificationView, lp);
}
public void refreshAllStatusBarIcons() {
@ -895,52 +887,31 @@ public class PhoneStatusBar extends BaseStatusBar {
StatusBarIconView iconView = addNotificationViews(key, notification);
if (iconView == null) return;
boolean immersive = false;
try {
immersive = ActivityManagerNative.getDefault().isTopActivityImmersive();
if (DEBUG) {
Log.d(TAG, "Top activity is " + (immersive?"immersive":"not immersive"));
}
} catch (RemoteException ex) {
}
/*
* DISABLED due to missing API
if (ENABLE_INTRUDERS && (
// TODO(dsandler): Only if the screen is on
notification.notification.intruderView != null)) {
Log.d(TAG, "Presenting high-priority notification");
// special new transient ticker mode
// 1. Populate mIntruderAlertView
if (notification.notification.intruderView == null) {
Log.e(TAG, notification.notification.toString() + " wanted to intrude but intruderView was null");
return;
}
if (mUseHeadsUp && shouldInterrupt(notification)) {
if (DEBUG) Log.d(TAG, "launching notification in heads up mode");
// 1. Populate mHeadsUpNotificationView
// bind the click event to the content area
PendingIntent contentIntent = notification.notification.contentIntent;
PendingIntent contentIntent = notification.getNotification().contentIntent;
final View.OnClickListener listener = (contentIntent != null)
? new NotificationClicker(contentIntent,
notification.pkg, notification.tag, notification.id)
notification.getPackageName(), notification.getTag(), notification.getId())
: null;
mIntruderAlertView.applyIntruderContent(notification.notification.intruderView, listener);
if (mHeadsUpNotificationView.applyContent(notification.getNotification(), listener)) {
mCurrentlyIntrudingNotification = notification;
mCurrentlyInterruptingNotification = notification;
// 2. Animate mIntruderAlertView in
mHandler.sendEmptyMessage(MSG_SHOW_INTRUDER);
// 2. Animate mHeadsUpNotificationView in
mHandler.sendEmptyMessage(MSG_SHOW_HEADS_UP);
// 3. Set alarm to age the notification off (TODO)
mHandler.removeMessages(MSG_HIDE_INTRUDER);
if (INTRUDER_ALERT_DECAY_MS > 0) {
mHandler.sendEmptyMessageDelayed(MSG_HIDE_INTRUDER, INTRUDER_ALERT_DECAY_MS);
// 3. Set alarm to age the notification off (TODO)
mHandler.removeMessages(MSG_HIDE_HEADS_UP);
if (HEADS_UP_DECAY_MS > 0) {
mHandler.sendEmptyMessageDelayed(MSG_HIDE_HEADS_UP, HEADS_UP_DECAY_MS);
}
}
} else
*/
if (notification.getNotification().fullScreenIntent != null) {
} else if (notification.getNotification().fullScreenIntent != null) {
// Stop screensaver if the notification has a full-screen intent.
// (like an incoming phone call)
awakenDreams();
@ -954,8 +925,8 @@ public class PhoneStatusBar extends BaseStatusBar {
} else {
// usual case: status bar visible & not immersive
// show the ticker if there isn't an intruder too
if (mCurrentlyIntrudingNotification == null) {
// show the ticker if there isn't already a heads up
if (mCurrentlyInterruptingNotification == null) {
tick(null, notification, true);
}
}
@ -976,8 +947,8 @@ public class PhoneStatusBar extends BaseStatusBar {
// Recalculate the position of the sliding windows and the titles.
updateExpandedViewPos(EXPANDED_LEAVE_ALONE);
if (ENABLE_INTRUDERS && old == mCurrentlyIntrudingNotification) {
mHandler.sendEmptyMessage(MSG_HIDE_INTRUDER);
if (ENABLE_HEADS_UP && old == mCurrentlyInterruptingNotification) {
mHandler.sendEmptyMessage(MSG_HIDE_HEADS_UP);
}
if (CLOSE_PANEL_WHEN_EMPTIED && mNotificationData.size() == 0) {
@ -1359,12 +1330,12 @@ public class PhoneStatusBar extends BaseStatusBar {
case MSG_CLOSE_PANELS:
animateCollapsePanels();
break;
case MSG_SHOW_INTRUDER:
setIntruderAlertVisibility(true);
case MSG_SHOW_HEADS_UP:
setHeadsUpVisibility(true);
break;
case MSG_HIDE_INTRUDER:
setIntruderAlertVisibility(false);
mCurrentlyIntrudingNotification = null;
case MSG_HIDE_HEADS_UP:
setHeadsUpVisibility(false);
mCurrentlyInterruptingNotification = null;
break;
}
}
@ -2487,22 +2458,20 @@ public class PhoneStatusBar extends BaseStatusBar {
mCurrentUserId);
}
private void setIntruderAlertVisibility(boolean vis) {
if (!ENABLE_INTRUDERS) return;
if (DEBUG) {
Log.v(TAG, (vis ? "showing" : "hiding") + " intruder alert window");
}
mIntruderAlertView.setVisibility(vis ? View.VISIBLE : View.GONE);
private void setHeadsUpVisibility(boolean vis) {
if (!ENABLE_HEADS_UP) return;
if (DEBUG) Log.v(TAG, (vis ? "showing" : "hiding") + " heads up window");
mHeadsUpNotificationView.setVisibility(vis ? View.VISIBLE : View.GONE);
}
public void dismissIntruder() {
if (mCurrentlyIntrudingNotification == null) return;
public void dismissHeadsUp() {
if (mCurrentlyInterruptingNotification == null) return;
try {
mBarService.onNotificationClear(
mCurrentlyIntrudingNotification.getPackageName(),
mCurrentlyIntrudingNotification.getTag(),
mCurrentlyIntrudingNotification.getId());
mCurrentlyInterruptingNotification.getPackageName(),
mCurrentlyInterruptingNotification.getTag(),
mCurrentlyInterruptingNotification.getId());
} catch (android.os.RemoteException ex) {
// oh well
}

View File

@ -16,6 +16,7 @@
package com.android.systemui.statusbar.policy;
import android.app.Notification;
import android.content.Context;
import android.content.res.Configuration;
import android.graphics.Rect;
@ -27,14 +28,13 @@ import android.view.View;
import android.view.ViewConfiguration;
import android.view.ViewGroup;
import android.widget.LinearLayout;
import android.widget.RemoteViews;
import com.android.systemui.R;
import com.android.systemui.SwipeHelper;
import com.android.systemui.statusbar.BaseStatusBar;
public class IntruderAlertView extends LinearLayout implements SwipeHelper.Callback {
private static final String TAG = "IntruderAlertView";
public class HeadsUpNotificationView extends LinearLayout implements SwipeHelper.Callback {
private static final String TAG = "HeadsUpNotificationView";
private static final boolean DEBUG = false;
Rect mTmpRect = new Rect();
@ -44,14 +44,14 @@ public class IntruderAlertView extends LinearLayout implements SwipeHelper.Callb
BaseStatusBar mBar;
private ViewGroup mContentHolder;
private RemoteViews mIntruderRemoteViews;
private Notification mHeadsUp;
private OnClickListener mOnClickListener;
public IntruderAlertView(Context context, AttributeSet attrs) {
public HeadsUpNotificationView(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public IntruderAlertView(Context context, AttributeSet attrs, int defStyle) {
public HeadsUpNotificationView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
setOrientation(LinearLayout.VERTICAL);
@ -64,9 +64,9 @@ public class IntruderAlertView extends LinearLayout implements SwipeHelper.Callb
mSwipeHelper = new SwipeHelper(SwipeHelper.X, this, densityScale, pagingTouchSlop);
mContentHolder = (ViewGroup) findViewById(R.id.contentHolder);
if (mIntruderRemoteViews != null) {
if (mHeadsUp != null) {
// whoops, we're on already!
applyIntruderContent(mIntruderRemoteViews, mOnClickListener);
applyContent(mHeadsUp, mOnClickListener);
}
}
@ -92,8 +92,8 @@ public class IntruderAlertView extends LinearLayout implements SwipeHelper.Callb
}
public void onChildDismissed(View v) {
Log.v(TAG, "User swiped intruder to dismiss");
mBar.dismissIntruder();
Log.v(TAG, "User swiped heads up to dismiss");
mBar.dismissHeadsUp();
}
public void onBeginDrag(View v) {
@ -134,33 +134,34 @@ public class IntruderAlertView extends LinearLayout implements SwipeHelper.Callb
}
}
public void applyIntruderContent(RemoteViews intruderView, OnClickListener listener) {
if (DEBUG) {
Log.v(TAG, "applyIntruderContent: view=" + intruderView + " listener=" + listener);
}
mIntruderRemoteViews = intruderView;
public boolean applyContent(Notification headsUp, OnClickListener listener) {
mHeadsUp = headsUp;
mOnClickListener = listener;
if (mContentHolder == null) {
if (mContentHolder == null) {
// too soon!
return;
return false;
}
if (headsUp.contentView == null) {
// bad data
return false;
}
mContentHolder.setX(0);
mContentHolder.setVisibility(View.VISIBLE);
mContentHolder.setAlpha(1f);
mContentHolder.removeAllViews();
final View content = intruderView.apply(getContext(), mContentHolder);
final View content = headsUp.contentView.apply(getContext(), mContentHolder);
if (listener != null) {
content.setOnClickListener(listener);
//content.setBackgroundResource(R.drawable.intruder_row_bg);
Drawable bg = getResources().getDrawable(R.drawable.intruder_row_bg);
Drawable bg = getResources().getDrawable(R.drawable.heads_up_notification_row_bg);
if (bg == null) {
Log.e(TAG, String.format("Can't find background drawable id=0x%08x", R.drawable.intruder_row_bg));
Log.e(TAG, String.format("Can't find background drawable id=0x%08x",
R.drawable.heads_up_notification_row_bg));
} else {
content.setBackgroundDrawable(bg);
}
}
mContentHolder.addView(content);
return true;
}
}