Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 0aac04ff authored by Adrian Roos's avatar Adrian Roos
Browse files

AOD: Show ambient versions of notifications

Introduces a new visible type that is shown on ambient display.

Bug: 30876804
Test: manual
Change-Id: I889e386430eda79bb362313d9834aa7ecd829871
parent c934c434
Loading
Loading
Loading
Loading
+3 −0
Original line number Diff line number Diff line
@@ -75,6 +75,9 @@
    <!-- Height of a large notification in the status bar -->
    <dimen name="notification_max_height">284dp</dimen>

    <!-- Height of an ambient notification on ambient display -->
    <dimen name="notification_ambient_height">400dp</dimen>

    <!-- Height of a heads up notification in the status bar for legacy custom views -->
    <dimen name="notification_max_heads_up_height_legacy">128dp</dimen>

+17 −0
Original line number Diff line number Diff line
@@ -1557,6 +1557,7 @@ public abstract class BaseStatusBar extends SystemUI implements
        final RemoteViews bigContentView = entry.cachedBigContentView;
        final RemoteViews headsUpContentView = entry.cachedHeadsUpContentView;
        final RemoteViews publicContentView = entry.cachedPublicContentView;
        final RemoteViews ambientContentView = entry.cachedAmbientContentView;

        if (contentView == null) {
            Log.v(TAG, "no contentView for: " + sbn.getNotification());
@@ -1637,6 +1638,7 @@ public abstract class BaseStatusBar extends SystemUI implements
        View bigContentViewLocal = null;
        View headsUpContentViewLocal = null;
        View publicViewLocal = null;
        View ambientViewLocal = null;
        try {
            contentViewLocal = contentView.apply(
                    sbn.getPackageContext(mContext),
@@ -1659,6 +1661,11 @@ public abstract class BaseStatusBar extends SystemUI implements
                        sbn.getPackageContext(mContext),
                        contentContainerPublic, mOnClickHandler);
            }
            if (ambientContentView != null) {
                ambientViewLocal = ambientContentView.apply(
                        sbn.getPackageContext(mContext),
                        contentContainer, mOnClickHandler);
            }

            if (contentViewLocal != null) {
                contentViewLocal.setIsRootNamespace(true);
@@ -1676,6 +1683,11 @@ public abstract class BaseStatusBar extends SystemUI implements
                publicViewLocal.setIsRootNamespace(true);
                contentContainerPublic.setContractedChild(publicViewLocal);
            }

            if (ambientViewLocal != null) {
                ambientViewLocal.setIsRootNamespace(true);
                contentContainer.setAmbientChild(ambientViewLocal);
            }
        }
        catch (RuntimeException e) {
            final String ident = sbn.getPackageName() + "/0x" + Integer.toHexString(sbn.getId());
@@ -2172,6 +2184,7 @@ public abstract class BaseStatusBar extends SystemUI implements
                row.setOnKeyguard(false);
                row.setSystemExpanded(visibleNotifications == 0 && !childNotification);
            }
            entry.row.setShowAmbient(isDozing());
            int userId = entry.notification.getUserId();
            boolean suppressedSummary = mGroupManager.isSummaryOfSuppressedGroup(
                    entry.notification) && !entry.row.isRemoved();
@@ -2209,6 +2222,10 @@ public abstract class BaseStatusBar extends SystemUI implements
        mStackScroller.changeViewPosition(mNotificationShelf, mStackScroller.getChildCount() - 3);
    }

    public boolean isDozing() {
        return false;
    }

    public boolean shouldShowOnKeyguard(StatusBarNotification sbn) {
        return mShowLockscreenNotifications && !mNotificationData.isAmbient(sbn.getKey());
    }
+21 −1
Original line number Diff line number Diff line
@@ -74,6 +74,7 @@ public class ExpandableNotificationRow extends ActivatableNotificationView {
    private int mMaxHeadsUpHeight;
    private int mNotificationMinHeight;
    private int mNotificationMaxHeight;
    private int mNotificationAmbientHeight;
    private int mIncreasedPaddingBetweenElements;

    /** Does this row contain layouts that can adapt to row expansion */
@@ -197,6 +198,7 @@ public class ExpandableNotificationRow extends ActivatableNotificationView {
    private float mContentTransformationAmount;
    private boolean mIconsVisible = true;
    private boolean mAboveShelf;
    private boolean mShowAmbient;
    private boolean mIsLastChild;
    private Runnable mOnDismissRunnable;

@@ -326,7 +328,8 @@ public class ExpandableNotificationRow extends ActivatableNotificationView {
                        != com.android.internal.R.id.status_bar_latest_event_content;
        int headsUpheight = headsUpCustom && beforeN ? mMaxHeadsUpHeightLegacy
                : mMaxHeadsUpHeight;
        layout.setHeights(minHeight, headsUpheight, mNotificationMaxHeight);
        layout.setHeights(minHeight, headsUpheight, mNotificationMaxHeight,
                mNotificationAmbientHeight);
    }

    public StatusBarNotification getStatusBarNotification() {
@@ -954,6 +957,7 @@ public class ExpandableNotificationRow extends ActivatableNotificationView {
        mNotificationMinHeightLegacy = getFontScaledHeight(R.dimen.notification_min_height_legacy);
        mNotificationMinHeight = getFontScaledHeight(R.dimen.notification_min_height);
        mNotificationMaxHeight = getFontScaledHeight(R.dimen.notification_max_height);
        mNotificationAmbientHeight = getFontScaledHeight(R.dimen.notification_ambient_height);
        mMaxHeadsUpHeightLegacy = getFontScaledHeight(
                R.dimen.notification_max_heads_up_height_legacy);
        mMaxHeadsUpHeight = getFontScaledHeight(R.dimen.notification_max_heads_up_height);
@@ -1353,6 +1357,8 @@ public class ExpandableNotificationRow extends ActivatableNotificationView {
            return mGuts.getHeight();
        } else if ((isChildInGroup() && !isGroupExpanded())) {
            return mPrivateLayout.getMinHeight();
        } else if (mShowAmbient) {
            return getAmbientHeight();
        } else if (mSensitive && mHideSensitiveForIntrinsicHeight) {
            return getMinHeight();
        } else if (mIsSummaryWithChildren && !mOnKeyguard) {
@@ -1683,6 +1689,13 @@ public class ExpandableNotificationRow extends ActivatableNotificationView {
        return showingLayout.getMinHeight();
    }

    private int getAmbientHeight() {
        NotificationContentView showingLayout = getShowingLayout();
        return showingLayout.getAmbientChild() != null
                ? showingLayout.getAmbientChild().getHeight()
                : getCollapsedHeight();
    }

    @Override
    public int getCollapsedHeight() {
        if (mIsSummaryWithChildren && !mShowingPublic) {
@@ -1879,6 +1892,13 @@ public class ExpandableNotificationRow extends ActivatableNotificationView {
        return mIsPinned || mHeadsupDisappearRunning || (mIsHeadsUp && mAboveShelf);
    }

    public void setShowAmbient(boolean showAmbient) {
        if (showAmbient != mShowAmbient) {
            mShowAmbient = showAmbient;
            notifyHeightChanged(false /* needsAnimation */);
        }
    }

    public void setAboveShelf(boolean aboveShelf) {
        mAboveShelf = aboveShelf;
    }
+87 −46
Original line number Diff line number Diff line
@@ -52,6 +52,7 @@ public class NotificationContentView extends FrameLayout {
    private static final int VISIBLE_TYPE_EXPANDED = 1;
    private static final int VISIBLE_TYPE_HEADSUP = 2;
    private static final int VISIBLE_TYPE_SINGLELINE = 3;
    private static final int VISIBLE_TYPE_AMBIENT = 4;
    public static final int UNDEFINED = -1;

    private final Rect mClipBounds = new Rect();
@@ -62,6 +63,7 @@ public class NotificationContentView extends FrameLayout {
    private View mExpandedChild;
    private View mHeadsUpChild;
    private HybridNotificationView mSingleLineView;
    private View mAmbientChild;

    private RemoteInputView mExpandedRemoteInput;
    private RemoteInputView mHeadsUpRemoteInput;
@@ -69,6 +71,7 @@ public class NotificationContentView extends FrameLayout {
    private NotificationViewWrapper mContractedWrapper;
    private NotificationViewWrapper mExpandedWrapper;
    private NotificationViewWrapper mHeadsUpWrapper;
    private NotificationViewWrapper mAmbientWrapper;
    private HybridGroupManager mHybridGroupManager;
    private int mClipTopAmount;
    private int mContentHeight;
@@ -81,6 +84,7 @@ public class NotificationContentView extends FrameLayout {
    private int mSmallHeight;
    private int mHeadsUpHeight;
    private int mNotificationMaxHeight;
    private int mNotificationAmbientHeight;
    private StatusBarNotification mStatusBarNotification;
    private NotificationGroupManager mGroupManager;
    private RemoteInputController mRemoteInputController;
@@ -136,10 +140,12 @@ public class NotificationContentView extends FrameLayout {
        reset();
    }

    public void setHeights(int smallHeight, int headsUpMaxHeight, int maxHeight) {
    public void setHeights(int smallHeight, int headsUpMaxHeight, int maxHeight,
            int ambientHeight) {
        mSmallHeight = smallHeight;
        mHeadsUpHeight = headsUpMaxHeight;
        mNotificationMaxHeight = maxHeight;
        mNotificationAmbientHeight = ambientHeight;
    }

    @Override
@@ -215,6 +221,17 @@ public class NotificationContentView extends FrameLayout {
                    MeasureSpec.makeMeasureSpec(maxSize, MeasureSpec.AT_MOST));
            maxChildHeight = Math.max(maxChildHeight, mSingleLineView.getMeasuredHeight());
        }
        if (mAmbientChild != null) {
            int size = Math.min(maxSize, mNotificationAmbientHeight);
            ViewGroup.LayoutParams layoutParams = mAmbientChild.getLayoutParams();
            if (layoutParams.height >= 0) {
                // An actual height is set
                size = Math.min(size, layoutParams.height);
            }
            mAmbientChild.measure(widthMeasureSpec,
                    MeasureSpec.makeMeasureSpec(size, MeasureSpec.AT_MOST));
            maxChildHeight = Math.max(maxChildHeight, mAmbientChild.getMeasuredHeight());
        }
        int ownHeight = Math.min(maxChildHeight, maxSize);
        setMeasuredDimension(width, ownHeight);
    }
@@ -344,6 +361,10 @@ public class NotificationContentView extends FrameLayout {
        return mHeadsUpChild;
    }

    public View getAmbientChild() {
        return mAmbientChild;
    }

    public void setContractedChild(View child) {
        if (mContractedChild != null) {
            mContractedChild.animate().cancel();
@@ -378,6 +399,17 @@ public class NotificationContentView extends FrameLayout {
                mContainingNotification);
    }

    public void setAmbientChild(View child) {
        if (mAmbientChild != null) {
            mAmbientChild.animate().cancel();
            removeView(mAmbientChild);
        }
        addView(child);
        mAmbientChild = child;
        mAmbientWrapper = NotificationViewWrapper.wrap(getContext(), child,
                mContainingNotification);
    }

    @Override
    protected void onVisibilityChanged(View changedView, int visibility) {
        super.onVisibilityChanged(changedView, visibility);
@@ -452,6 +484,11 @@ public class NotificationContentView extends FrameLayout {
                        com.android.internal.R.dimen.notification_action_list_height);
        }

        if (isVisibleOrTransitioning(VISIBLE_TYPE_AMBIENT)) {
            return mContractedChild.getHeight() + mContext.getResources().getDimensionPixelSize(
                    com.android.internal.R.dimen.notification_action_list_height);
        }

        // Transition between heads-up & expanded, or pinned.
        if (mHeadsUpChild != null && mExpandedChild != null) {
            boolean transitioningBetweenHunAndExpanded =
@@ -656,39 +693,23 @@ public class NotificationContentView extends FrameLayout {
    }

    private void forceUpdateVisibilities() {
        boolean contractedVisible = mVisibleType == VISIBLE_TYPE_CONTRACTED
                || mTransformationStartVisibleType == VISIBLE_TYPE_CONTRACTED;
        boolean expandedVisible = mVisibleType == VISIBLE_TYPE_EXPANDED
                || mTransformationStartVisibleType == VISIBLE_TYPE_EXPANDED;
        boolean headsUpVisible = mVisibleType == VISIBLE_TYPE_HEADSUP
                || mTransformationStartVisibleType == VISIBLE_TYPE_HEADSUP;
        boolean singleLineVisible = mVisibleType == VISIBLE_TYPE_SINGLELINE
                || mTransformationStartVisibleType == VISIBLE_TYPE_SINGLELINE;
        if (!contractedVisible) {
            mContractedChild.setVisibility(View.INVISIBLE);
        } else {
            mContractedWrapper.setVisible(true);
        }
        if (mExpandedChild != null) {
            if (!expandedVisible) {
                mExpandedChild.setVisibility(View.INVISIBLE);
            } else {
                mExpandedWrapper.setVisible(true);
            }
        }
        if (mHeadsUpChild != null) {
            if (!headsUpVisible) {
                mHeadsUpChild.setVisibility(View.INVISIBLE);
            } else {
                mHeadsUpWrapper.setVisible(true);
        forceUpdateVisibility(VISIBLE_TYPE_CONTRACTED, mContractedChild, mContractedWrapper);
        forceUpdateVisibility(VISIBLE_TYPE_EXPANDED, mExpandedChild, mExpandedWrapper);
        forceUpdateVisibility(VISIBLE_TYPE_HEADSUP, mHeadsUpChild, mHeadsUpWrapper);
        forceUpdateVisibility(VISIBLE_TYPE_SINGLELINE, mSingleLineView, mSingleLineView);
        forceUpdateVisibility(VISIBLE_TYPE_AMBIENT, mAmbientChild, mAmbientWrapper);
    }

    private void forceUpdateVisibility(int type, View view, TransformableView wrapper) {
        if (view == null) {
            return;
        }
        if (mSingleLineView != null) {
            if (!singleLineVisible) {
                mSingleLineView.setVisibility(View.INVISIBLE);
        boolean visible = mVisibleType == type
                || mTransformationStartVisibleType == type;
        if (!visible) {
            view.setVisibility(INVISIBLE);
        } else {
                mSingleLineView.setVisible(true);
            }
            wrapper.setVisible(true);
        }
    }

@@ -722,19 +743,22 @@ public class NotificationContentView extends FrameLayout {
    }

    private void updateViewVisibilities(int visibleType) {
        boolean contractedVisible = visibleType == VISIBLE_TYPE_CONTRACTED;
        mContractedWrapper.setVisible(contractedVisible);
        if (mExpandedChild != null) {
            boolean expandedVisible = visibleType == VISIBLE_TYPE_EXPANDED;
            mExpandedWrapper.setVisible(expandedVisible);
        updateViewVisibility(visibleType, VISIBLE_TYPE_CONTRACTED,
                mContractedChild, mContractedWrapper);
        updateViewVisibility(visibleType, VISIBLE_TYPE_EXPANDED,
                mExpandedChild, mExpandedWrapper);
        updateViewVisibility(visibleType, VISIBLE_TYPE_HEADSUP,
                mHeadsUpChild, mHeadsUpWrapper);
        updateViewVisibility(visibleType, VISIBLE_TYPE_SINGLELINE,
                mSingleLineView, mSingleLineView);
        updateViewVisibility(visibleType, VISIBLE_TYPE_AMBIENT,
                mAmbientChild, mAmbientWrapper);
    }
        if (mHeadsUpChild != null) {
            boolean headsUpVisible = visibleType == VISIBLE_TYPE_HEADSUP;
            mHeadsUpWrapper.setVisible(headsUpVisible);
        }
        if (mSingleLineView != null) {
            boolean singleLineVisible = visibleType == VISIBLE_TYPE_SINGLELINE;
            mSingleLineView.setVisible(singleLineVisible);

    private void updateViewVisibility(int visibleType, int type, View view,
            TransformableView wrapper) {
        if (view != null) {
            wrapper.setVisible(visibleType == type);
        }
    }

@@ -784,6 +808,8 @@ public class NotificationContentView extends FrameLayout {
                return mHeadsUpWrapper;
            case VISIBLE_TYPE_SINGLELINE:
                return mSingleLineView;
            case VISIBLE_TYPE_AMBIENT:
                return mAmbientWrapper;
            default:
                return mContractedWrapper;
        }
@@ -801,6 +827,8 @@ public class NotificationContentView extends FrameLayout {
                return mHeadsUpChild;
            case VISIBLE_TYPE_SINGLELINE:
                return mSingleLineView;
            case VISIBLE_TYPE_AMBIENT:
                return mAmbientChild;
            default:
                return mContractedChild;
        }
@@ -814,6 +842,8 @@ public class NotificationContentView extends FrameLayout {
                return mHeadsUpWrapper;
            case VISIBLE_TYPE_CONTRACTED:
                return mContractedWrapper;
            case VISIBLE_TYPE_AMBIENT:
                return mAmbientWrapper;
            default:
                return null;
        }
@@ -823,6 +853,10 @@ public class NotificationContentView extends FrameLayout {
     * @return one of the static enum types in this view, calculated form the current state
     */
    public int calculateVisibleType() {
        if (mDark && !mIsChildInGroup) {
            // TODO: Handle notification groups
            return VISIBLE_TYPE_AMBIENT;
        }
        if (mUserExpanding) {
            int height = !mIsChildInGroup || isGroupExpanded()
                    || mContainingNotification.isExpanded(true /* allowOnKeyguard */)
@@ -895,6 +929,7 @@ public class NotificationContentView extends FrameLayout {
        if (mSingleLineView != null && (mVisibleType == VISIBLE_TYPE_SINGLELINE || !dark)) {
            mSingleLineView.setDark(dark, fade, delay);
        }
        selectLayout(!dark && fade /* animate */, false /* force */);
    }

    public void setHeadsUp(boolean headsUp) {
@@ -947,6 +982,9 @@ public class NotificationContentView extends FrameLayout {
        if (mHeadsUpChild != null) {
            mHeadsUpWrapper.notifyContentUpdated(entry.notification);
        }
        if (mAmbientChild != null) {
            mAmbientWrapper.notifyContentUpdated(entry.notification);
        }
        updateShowingLegacyBackground();
        mForceSelectNextLayout = true;
        setDark(mDark, false /* animate */, 0 /* delay */);
@@ -1133,6 +1171,9 @@ public class NotificationContentView extends FrameLayout {
        if (header == null && mHeadsUpChild != null) {
            header = mHeadsUpWrapper.getNotificationHeader();
        }
        if (header == null && mAmbientChild != null) {
            header = mAmbientWrapper.getNotificationHeader();
        }
        return header;
    }

+6 −0
Original line number Diff line number Diff line
@@ -67,6 +67,7 @@ public class NotificationData {
        public RemoteViews cachedBigContentView;
        public RemoteViews cachedHeadsUpContentView;
        public RemoteViews cachedPublicContentView;
        public RemoteViews cachedAmbientContentView;
        public CharSequence remoteInputText;
        private int mCachedContrastColor = COLOR_INVALID;
        private int mCachedContrastColorIsFor = COLOR_INVALID;
@@ -126,6 +127,8 @@ public class NotificationData {
                        updatedNotificationBuilder.createHeadsUpContentView();
                final RemoteViews newPublicNotification
                        = updatedNotificationBuilder.makePublicContentView();
                final RemoteViews newAmbientNotification
                        = updatedNotificationBuilder.makeAmbientNotification();

                boolean sameCustomView = Objects.equals(
                        notification.getNotification().extras.getBoolean(
@@ -136,11 +139,13 @@ public class NotificationData {
                        && compareRemoteViews(cachedBigContentView, newBigContentView)
                        && compareRemoteViews(cachedHeadsUpContentView, newHeadsUpContentView)
                        && compareRemoteViews(cachedPublicContentView, newPublicNotification)
                        && compareRemoteViews(cachedAmbientContentView, newAmbientNotification)
                        && sameCustomView;
                cachedPublicContentView = newPublicNotification;
                cachedHeadsUpContentView = newHeadsUpContentView;
                cachedBigContentView = newBigContentView;
                cachedContentView = newContentView;
                cachedAmbientContentView = newAmbientNotification;
            } else {
                final Notification.Builder builder
                        = Notification.Builder.recoverBuilder(ctx, notification.getNotification());
@@ -149,6 +154,7 @@ public class NotificationData {
                cachedBigContentView = builder.createBigContentView();
                cachedHeadsUpContentView = builder.createHeadsUpContentView();
                cachedPublicContentView = builder.makePublicContentView();
                cachedAmbientContentView = builder.makeAmbientNotification();

                applyInPlace = false;
            }
Loading