ExpandableNotificationRow.java revision d009ab1e2a57648cac9de93912964e2a36ae1762
151c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren/*
251c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren * Copyright (C) 2013 The Android Open Source Project
351c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren *
451c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren * Licensed under the Apache License, Version 2.0 (the "License");
551c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren * you may not use this file except in compliance with the License.
651c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren * You may obtain a copy of the License at
751c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren *
851c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren *      http://www.apache.org/licenses/LICENSE-2.0
951c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren *
1051c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren * Unless required by applicable law or agreed to in writing, software
1151c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren * distributed under the License is distributed on an "AS IS" BASIS,
1251c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1351c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren * See the License for the specific language governing permissions and
1451c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren * limitations under the License.
1551c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren */
1651c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren
1751c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wrenpackage com.android.systemui.statusbar;
1851c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren
194b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellorimport android.animation.Animator;
204b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellorimport android.animation.AnimatorListenerAdapter;
214b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellorimport android.animation.AnimatorSet;
224b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellorimport android.animation.ObjectAnimator;
234b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellorimport android.animation.ValueAnimator;
244b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellorimport android.animation.ValueAnimator.AnimatorUpdateListener;
25a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinekimport android.app.Notification;
2651c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wrenimport android.content.Context;
27cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinekimport android.graphics.drawable.AnimatedVectorDrawable;
28cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinekimport android.graphics.drawable.AnimationDrawable;
29b5605e58cb8080c8c887b1885336b707596c8094Selim Cinekimport android.graphics.drawable.ColorDrawable;
30cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinekimport android.graphics.drawable.Drawable;
31da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinekimport android.os.Build;
32b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggiimport android.service.notification.StatusBarNotification;
3351c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wrenimport android.util.AttributeSet;
3401af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinekimport android.view.LayoutInflater;
356183d12926a189b08cc3be8d9c78470617e63db0Selim Cinekimport android.view.MotionEvent;
36eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinekimport android.view.NotificationHeaderView;
37a5e0f415d351ad1a9c0ffde8d93df91a2384591fDan Sandlerimport android.view.View;
38b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggiimport android.view.ViewStub;
39fe40f7d13bfc1faa35c9a131ce4be5104cb8f6b9Jorim Jaggiimport android.view.accessibility.AccessibilityEvent;
4098713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinekimport android.widget.Chronometer;
41cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinekimport android.widget.ImageView;
42eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinekimport android.widget.RemoteViews;
43b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
444bb593492ccf560382fac9ae533a7429cec53c94Selim Cinekimport com.android.internal.util.NotificationColorUtil;
45a5e0f415d351ad1a9c0ffde8d93df91a2384591fDan Sandlerimport com.android.systemui.R;
460e2ffbd48bbedf47deb7f6aed96bd07e2fc96f53Blazej Magnowskiimport com.android.systemui.classifier.FalsingManager;
47c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinekimport com.android.systemui.statusbar.notification.HybridNotificationView;
480ffbda62e55ad390e05e6c3ff52e1378e420285cSelim Cinekimport com.android.systemui.statusbar.notification.NotificationViewWrapper;
49b5605e58cb8080c8c887b1885336b707596c8094Selim Cinekimport com.android.systemui.statusbar.phone.NotificationGroupManager;
5031aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinekimport com.android.systemui.statusbar.policy.HeadsUpManager;
51b5605e58cb8080c8c887b1885336b707596c8094Selim Cinekimport com.android.systemui.statusbar.stack.NotificationChildrenContainer;
52b5605e58cb8080c8c887b1885336b707596c8094Selim Cinekimport com.android.systemui.statusbar.stack.StackScrollState;
53b5605e58cb8080c8c887b1885336b707596c8094Selim Cinekimport com.android.systemui.statusbar.stack.StackStateAnimator;
54b5605e58cb8080c8c887b1885336b707596c8094Selim Cinekimport com.android.systemui.statusbar.stack.StackViewState;
55b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
564b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellorimport java.util.ArrayList;
57b5605e58cb8080c8c887b1885336b707596c8094Selim Cinekimport java.util.List;
58a5e0f415d351ad1a9c0ffde8d93df91a2384591fDan Sandler
594222d9a7fb87d73e1443ec1a2de9782b05741af6Jorim Jaggipublic class ExpandableNotificationRow extends ActivatableNotificationView {
60b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
61b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    private static final int DEFAULT_DIVIDER_ALPHA = 0x29;
62b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    private static final int COLORED_DIVIDER_ALPHA = 0x7B;
6301af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek    private int mNotificationMinHeightLegacy;
6401af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek    private int mMaxHeadsUpHeightLegacy;
6501af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek    private int mMaxHeadsUpHeight;
6601af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek    private int mNotificationMinHeight;
6701af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek    private int mNotificationMaxHeight;
6851c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren
691685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    /** Does this row contain layouts that can adapt to row expansion */
7051c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    private boolean mExpandable;
711685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    /** Has the user actively changed the expansion state of this row */
721685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    private boolean mHasUserChangedExpansion;
731685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    /** If {@link #mHasUserChangedExpansion}, has the user expanded this row */
7451c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    private boolean mUserExpanded;
7531aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek
7631aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek    /**
7731aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek     * Has this notification been expanded while it was pinned
7831aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek     */
7931aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek    private boolean mExpandedWhenPinned;
801685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    /** Is the user touching this row */
8151c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    private boolean mUserLocked;
821685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    /** Are we showing the "public" version */
83a5e0f415d351ad1a9c0ffde8d93df91a2384591fDan Sandler    private boolean mShowingPublic;
84ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi    private boolean mSensitive;
853c76d509d362cf5086a63722ab41e04f5d539182Selim Cinek    private boolean mSensitiveHiddenInGeneral;
86ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi    private boolean mShowingPublicInitialized;
8760122be6747c4f79b96f6808158f8f7e7548b7d3Selim Cinek    private boolean mHideSensitiveForIntrinsicHeight;
8851c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren
891685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    /**
901685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * Is this notification expanded by the system. The expansion state can be overridden by the
911685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * user expansion.
921685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     */
931685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    private boolean mIsSystemExpanded;
94dce3c4cca5d4df4cc49c1a9f0537e2fecdbc45d2Jorim Jaggi
95dce3c4cca5d4df4cc49c1a9f0537e2fecdbc45d2Jorim Jaggi    /**
9683bc78338437a460076a4b5778ded38440ac3501Selim Cinek     * Whether the notification is on the keyguard and the expansion is disabled.
97dce3c4cca5d4df4cc49c1a9f0537e2fecdbc45d2Jorim Jaggi     */
9883bc78338437a460076a4b5778ded38440ac3501Selim Cinek    private boolean mOnKeyguard;
99dce3c4cca5d4df4cc49c1a9f0537e2fecdbc45d2Jorim Jaggi
1004b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    private AnimatorSet mTranslateAnim;
1014b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    private ArrayList<View> mTranslateableViews;
102be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi    private NotificationContentView mPublicLayout;
103be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi    private NotificationContentView mPrivateLayout;
1041685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    private int mMaxExpandHeight;
1058d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek    private int mHeadsUpHeight;
106863834bd96bdebcf21f4c4a7d8285d4858c061e4Selim Cinek    private View mVetoButton;
1074bb593492ccf560382fac9ae533a7429cec53c94Selim Cinek    private int mNotificationColor;
1080d3e62f3e07a69f21c1b1dfa2c8c0fb8b6c95655Dan Sandler    private boolean mClearable;
10978403d79739605511ea88b653564d81d7bf4bbbaChris Wren    private ExpansionLogger mLogger;
11078403d79739605511ea88b653564d81d7bf4bbbaChris Wren    private String mLoggingKey;
1114b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    private NotificationSettingsIconRow mSettingsIconRow;
1128d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek    private NotificationGuts mGuts;
113da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek    private NotificationData.Entry mEntry;
114b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi    private StatusBarNotification mStatusBarNotification;
1153fd273e6113fb1b8986314a03ab6d7e90efd0beaMady Mellor    private String mAppName;
1161a521f3ea841f6db9686bbec7f950a3883d075aaSelim Cinek    private boolean mIsHeadsUp;
11798713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek    private boolean mLastChronometerRunning = true;
118eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek    private NotificationHeaderView mNotificationHeader;
1199c7712d45ccec56a80873a83e56a83f810624b43Selim Cinek    private NotificationViewWrapper mNotificationHeaderWrapper;
120b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    private ViewStub mChildrenContainerStub;
121b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    private NotificationGroupManager mGroupManager;
122b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    private boolean mChildrenExpanded;
123263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek    private boolean mIsSummaryWithChildren;
124b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    private NotificationChildrenContainer mChildrenContainer;
1254b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    private ViewStub mSettingsIconRowStub;
126ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek    private ViewStub mGutsStub;
127b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    private boolean mIsSystemChildExpanded;
128684a442b812a5e95d813700ffa2fd17ca72048a7Selim Cinek    private boolean mIsPinned;
1290e2ffbd48bbedf47deb7f6aed96bd07e2fc96f53Blazej Magnowski    private FalsingManager mFalsingManager;
13031aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek    private HeadsUpManager mHeadsUpManager;
131ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek    private NotificationHeaderUtil mHeaderUtil = new NotificationHeaderUtil(this);
132b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi
1335eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi    private boolean mJustClicked;
1345a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek    private boolean mIconAnimationRunning;
13534d93b0985063090a9bad88a1b80e1b99bae3332Selim Cinek    private boolean mShowNoBackground;
136388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek    private ExpandableNotificationRow mNotificationParent;
137570981d5f1bcd0e5186cc02655254a0606b6ec14Selim Cinek    private OnExpandClickListener mOnExpandClickListener;
138eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek    private OnClickListener mExpandClickListener = new OnClickListener() {
139eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        @Override
140eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        public void onClick(View v) {
141624c02db7f1d24ec1e307530ff32d4fd5859feaeSelim Cinek            if (!mShowingPublic && mGroupManager.isSummaryOfGroup(mStatusBarNotification)) {
142eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek                mGroupManager.toggleGroupExpansion(mStatusBarNotification);
14331aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek                mOnExpandClickListener.onExpandClicked(mEntry,
144570981d5f1bcd0e5186cc02655254a0606b6ec14Selim Cinek                        mGroupManager.isGroupExpanded(mStatusBarNotification));
145eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek            } else {
14631aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek                boolean nowExpanded;
14731aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek                if (isPinned()) {
14831aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek                    nowExpanded = !mExpandedWhenPinned;
14931aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek                    mExpandedWhenPinned = nowExpanded;
15031aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek                } else {
15131aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek                    nowExpanded = !isExpanded();
15231aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek                    setUserExpanded(nowExpanded);
15331aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek                }
154eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek                notifyHeightChanged(true);
15531aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek                mOnExpandClickListener.onExpandClicked(mEntry, nowExpanded);
156eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek            }
157eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        }
158eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek    };
1591b2a05eb00746756c4d37ad76d597d909019e56fSelim Cinek    private boolean mForceUnlocked;
1603f19f60d654421eee5b35a92129081f08c977629Selim Cinek    private boolean mDismissed;
1613f19f60d654421eee5b35a92129081f08c977629Selim Cinek    private boolean mKeepInParent;
1623f19f60d654421eee5b35a92129081f08c977629Selim Cinek    private boolean mRemoved;
1635eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi
1648d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek    public NotificationContentView getPrivateLayout() {
1658d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek        return mPrivateLayout;
1668d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek    }
1678d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek
1688d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek    public NotificationContentView getPublicLayout() {
1698d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek        return mPublicLayout;
1708d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek    }
1718d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek
172cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek    public void setIconAnimationRunning(boolean running) {
173cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek        setIconAnimationRunning(running, mPublicLayout);
174cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek        setIconAnimationRunning(running, mPrivateLayout);
1755a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek        setIconAnimationRunningForChild(running, mNotificationHeader);
1765a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek        if (mIsSummaryWithChildren) {
1775a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek            List<ExpandableNotificationRow> notificationChildren =
1785a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek                    mChildrenContainer.getNotificationChildren();
1795a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek            for (int i = 0; i < notificationChildren.size(); i++) {
1805a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek                ExpandableNotificationRow child = notificationChildren.get(i);
1815a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek                child.setIconAnimationRunning(running);
1825a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek            }
1835a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek        }
1845a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek        mIconAnimationRunning = running;
185cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek    }
186cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek
187cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek    private void setIconAnimationRunning(boolean running, NotificationContentView layout) {
188cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek        if (layout != null) {
189cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek            View contractedChild = layout.getContractedChild();
190cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek            View expandedChild = layout.getExpandedChild();
1918d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek            View headsUpChild = layout.getHeadsUpChild();
192cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek            setIconAnimationRunningForChild(running, contractedChild);
193cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek            setIconAnimationRunningForChild(running, expandedChild);
1948d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek            setIconAnimationRunningForChild(running, headsUpChild);
195cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek        }
196cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek    }
197cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek
198cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek    private void setIconAnimationRunningForChild(boolean running, View child) {
199cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek        if (child != null) {
200cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek            ImageView icon = (ImageView) child.findViewById(com.android.internal.R.id.icon);
201cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek            setIconRunning(icon, running);
202cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek            ImageView rightIcon = (ImageView) child.findViewById(
203cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                    com.android.internal.R.id.right_icon);
204cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek            setIconRunning(rightIcon, running);
205cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek        }
206cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek    }
207cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek
208cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek    private void setIconRunning(ImageView imageView, boolean running) {
209cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek        if (imageView != null) {
210cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek            Drawable drawable = imageView.getDrawable();
211cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek            if (drawable instanceof AnimationDrawable) {
212cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                AnimationDrawable animationDrawable = (AnimationDrawable) drawable;
213cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                if (running) {
214cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                    animationDrawable.start();
215cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                } else {
216cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                    animationDrawable.stop();
217cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                }
218cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek            } else if (drawable instanceof AnimatedVectorDrawable) {
219cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                AnimatedVectorDrawable animationDrawable = (AnimatedVectorDrawable) drawable;
220cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                if (running) {
221cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                    animationDrawable.start();
222cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                } else {
223cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                    animationDrawable.stop();
224cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek                }
225cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek            }
226cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek        }
227cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek    }
228cab4a60c485872848fc0fa3e65baaeb06d21a7d8Selim Cinek
229da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek    public void onNotificationUpdated(NotificationData.Entry entry) {
230da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek        mEntry = entry;
231da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek        mStatusBarNotification = entry.notification;
232b88b1a1dbde3364cd92d6a69a41ef2d4e2877294Adrian Roos        mPrivateLayout.onNotificationUpdated(entry);
233b88b1a1dbde3364cd92d6a69a41ef2d4e2877294Adrian Roos        mPublicLayout.onNotificationUpdated(entry);
234757d879966fdbff1b67c9ec6fd4b6c75152b991aSelim Cinek        mShowingPublicInitialized = false;
2354bb593492ccf560382fac9ae533a7429cec53c94Selim Cinek        updateNotificationColor();
236757d879966fdbff1b67c9ec6fd4b6c75152b991aSelim Cinek        updateClearability();
2378fc93c90839e5d9dd52bca9dd97c198c0fe68af1Selim Cinek        if (mIsSummaryWithChildren) {
2388fc93c90839e5d9dd52bca9dd97c198c0fe68af1Selim Cinek            recreateNotificationHeader();
239c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek            mChildrenContainer.onNotificationUpdated();
2408fc93c90839e5d9dd52bca9dd97c198c0fe68af1Selim Cinek        }
2415a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek        if (mIconAnimationRunning) {
2425a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek            setIconAnimationRunning(true);
2435a175d9d543c4438672990aa8a820bd1292bdd6aSelim Cinek        }
244ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek        if (mNotificationParent != null) {
245ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek            mNotificationParent.updateChildrenHeaderAppearance();
246ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek        }
247263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek        onChildrenCountChanged();
248624c02db7f1d24ec1e307530ff32d4fd5859feaeSelim Cinek        // The public layouts expand button is always visible
249624c02db7f1d24ec1e307530ff32d4fd5859feaeSelim Cinek        mPublicLayout.updateExpandButtons(true);
250da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek        updateLimits();
251da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek    }
252da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek
253da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek    private void updateLimits() {
254a1744872f4447dd370002a607c32776dffe519f5Selim Cinek        updateLimitsForView(mPrivateLayout);
255a1744872f4447dd370002a607c32776dffe519f5Selim Cinek        updateLimitsForView(mPublicLayout);
256a1744872f4447dd370002a607c32776dffe519f5Selim Cinek    }
257a1744872f4447dd370002a607c32776dffe519f5Selim Cinek
258a1744872f4447dd370002a607c32776dffe519f5Selim Cinek    private void updateLimitsForView(NotificationContentView layout) {
259a1744872f4447dd370002a607c32776dffe519f5Selim Cinek        boolean customView = layout.getContractedChild().getId()
260da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek                != com.android.internal.R.id.status_bar_latest_event_content;
261da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek        boolean beforeN = mEntry.targetSdk < Build.VERSION_CODES.N;
262da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek        int minHeight = customView && beforeN && !mIsSummaryWithChildren ?
263da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek                mNotificationMinHeightLegacy : mNotificationMinHeight;
264a1744872f4447dd370002a607c32776dffe519f5Selim Cinek        boolean headsUpCustom = layout.getHeadsUpChild() != null &&
265a1744872f4447dd370002a607c32776dffe519f5Selim Cinek                layout.getHeadsUpChild().getId()
266a1744872f4447dd370002a607c32776dffe519f5Selim Cinek                        != com.android.internal.R.id.status_bar_latest_event_content;
26777019c72332cb31dd1cb713ea4c66e267e6cbf39Selim Cinek        int headsUpheight = headsUpCustom && beforeN ? mMaxHeadsUpHeightLegacy
26877019c72332cb31dd1cb713ea4c66e267e6cbf39Selim Cinek                : mMaxHeadsUpHeight;
269a1744872f4447dd370002a607c32776dffe519f5Selim Cinek        layout.setHeights(minHeight, headsUpheight, mNotificationMaxHeight);
270b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi    }
271b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi
272b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi    public StatusBarNotification getStatusBarNotification() {
273b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi        return mStatusBarNotification;
274b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi    }
275b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi
276b8f09cf5533d458868a335ce334e4880b2b0788dSelim Cinek    public boolean isHeadsUp() {
277b8f09cf5533d458868a335ce334e4880b2b0788dSelim Cinek        return mIsHeadsUp;
278b8f09cf5533d458868a335ce334e4880b2b0788dSelim Cinek    }
279b8f09cf5533d458868a335ce334e4880b2b0788dSelim Cinek
2801a521f3ea841f6db9686bbec7f950a3883d075aaSelim Cinek    public void setHeadsUp(boolean isHeadsUp) {
281c80fdb11f55f4c1f3ca9b5cdc7035afa2a0b9e91Selim Cinek        int intrinsicBefore = getIntrinsicHeight();
2821a521f3ea841f6db9686bbec7f950a3883d075aaSelim Cinek        mIsHeadsUp = isHeadsUp;
2838d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek        mPrivateLayout.setHeadsUp(isHeadsUp);
284b41b2f6fc2bcce6da6d6ae855a2a36cfa6f7f99dSelim Cinek        if (mIsSummaryWithChildren) {
285b41b2f6fc2bcce6da6d6ae855a2a36cfa6f7f99dSelim Cinek            // The overflow might change since we allow more lines as HUN.
286b41b2f6fc2bcce6da6d6ae855a2a36cfa6f7f99dSelim Cinek            mChildrenContainer.updateGroupOverflow();
287b41b2f6fc2bcce6da6d6ae855a2a36cfa6f7f99dSelim Cinek        }
288c80fdb11f55f4c1f3ca9b5cdc7035afa2a0b9e91Selim Cinek        if (intrinsicBefore != getIntrinsicHeight()) {
289c80fdb11f55f4c1f3ca9b5cdc7035afa2a0b9e91Selim Cinek            notifyHeightChanged(false  /* needsAnimation */);
290c80fdb11f55f4c1f3ca9b5cdc7035afa2a0b9e91Selim Cinek        }
2911a521f3ea841f6db9686bbec7f950a3883d075aaSelim Cinek    }
2921a521f3ea841f6db9686bbec7f950a3883d075aaSelim Cinek
293b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public void setGroupManager(NotificationGroupManager groupManager) {
294b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        mGroupManager = groupManager;
29583bc78338437a460076a4b5778ded38440ac3501Selim Cinek        mPrivateLayout.setGroupManager(groupManager);
296b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
297b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
298b88b1a1dbde3364cd92d6a69a41ef2d4e2877294Adrian Roos    public void setRemoteInputController(RemoteInputController r) {
299b88b1a1dbde3364cd92d6a69a41ef2d4e2877294Adrian Roos        mPrivateLayout.setRemoteInputController(r);
300b88b1a1dbde3364cd92d6a69a41ef2d4e2877294Adrian Roos    }
301b88b1a1dbde3364cd92d6a69a41ef2d4e2877294Adrian Roos
3023fd273e6113fb1b8986314a03ab6d7e90efd0beaMady Mellor    public void setAppName(String appName) {
3033fd273e6113fb1b8986314a03ab6d7e90efd0beaMady Mellor        mAppName = appName;
3043fd273e6113fb1b8986314a03ab6d7e90efd0beaMady Mellor        if (mSettingsIconRow != null) {
3053fd273e6113fb1b8986314a03ab6d7e90efd0beaMady Mellor            mSettingsIconRow.setAppName(mAppName);
3063fd273e6113fb1b8986314a03ab6d7e90efd0beaMady Mellor        }
3073fd273e6113fb1b8986314a03ab6d7e90efd0beaMady Mellor    }
3083fd273e6113fb1b8986314a03ab6d7e90efd0beaMady Mellor
309b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public void addChildNotification(ExpandableNotificationRow row) {
310b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        addChildNotification(row, -1);
311b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
312b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
313b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    /**
314b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek     * Add a child notification to this view.
315b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek     *
316b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek     * @param row the row to add
317b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek     * @param childIndex the index to add it at, if -1 it will be added at the end
318b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek     */
319b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public void addChildNotification(ExpandableNotificationRow row, int childIndex) {
320b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        if (mChildrenContainer == null) {
321b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            mChildrenContainerStub.inflate();
322b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        }
323b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        mChildrenContainer.addNotification(row, childIndex);
324263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek        onChildrenCountChanged();
325263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek        row.setIsChildInGroup(true, this);
326b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
327b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
328b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public void removeChildNotification(ExpandableNotificationRow row) {
329b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        if (mChildrenContainer != null) {
330b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            mChildrenContainer.removeNotification(row);
331b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        }
332a5703187a9dba418f742fab0874a8f683b0bbb0eSelim Cinek        if (!row.isRemoved()) {
333a5703187a9dba418f742fab0874a8f683b0bbb0eSelim Cinek            mHeaderUtil.restoreNotificationHeader(row);
334a5703187a9dba418f742fab0874a8f683b0bbb0eSelim Cinek        }
335263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek        onChildrenCountChanged();
336263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek        row.setIsChildInGroup(false, null);
337263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek    }
338263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek
339263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek    public boolean isChildInGroup() {
340a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek        return mNotificationParent != null;
341263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek    }
342263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek
343388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek    public ExpandableNotificationRow getNotificationParent() {
344388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek        return mNotificationParent;
345388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek    }
346388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek
347263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek    /**
348263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek     * @param isChildInGroup Is this notification now in a group
349263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek     * @param parent the new parent notification
350263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek     */
351a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek    public void setIsChildInGroup(boolean isChildInGroup, ExpandableNotificationRow parent) {;
352a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek        boolean childInGroup = BaseStatusBar.ENABLE_CHILD_NOTIFICATIONS && isChildInGroup;
353a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek        mNotificationParent = childInGroup ? parent : null;
354a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek        mPrivateLayout.setIsChildInGroup(childInGroup);
355a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek        updateNoBackgroundState();
35634d93b0985063090a9bad88a1b80e1b99bae3332Selim Cinek    }
35734d93b0985063090a9bad88a1b80e1b99bae3332Selim Cinek
35834d93b0985063090a9bad88a1b80e1b99bae3332Selim Cinek    @Override
3597210947e0d0e384fc34d61160c99adc2f36734e0Selim Cinek    public boolean onTouchEvent(MotionEvent event) {
3607210947e0d0e384fc34d61160c99adc2f36734e0Selim Cinek        if (event.getActionMasked() != MotionEvent.ACTION_DOWN
3617210947e0d0e384fc34d61160c99adc2f36734e0Selim Cinek                || !isChildInGroup() || isGroupExpanded()) {
3627210947e0d0e384fc34d61160c99adc2f36734e0Selim Cinek            return super.onTouchEvent(event);
3637210947e0d0e384fc34d61160c99adc2f36734e0Selim Cinek        } else {
3647210947e0d0e384fc34d61160c99adc2f36734e0Selim Cinek            return false;
3657210947e0d0e384fc34d61160c99adc2f36734e0Selim Cinek        }
3667210947e0d0e384fc34d61160c99adc2f36734e0Selim Cinek    }
3677210947e0d0e384fc34d61160c99adc2f36734e0Selim Cinek
3687210947e0d0e384fc34d61160c99adc2f36734e0Selim Cinek    @Override
369f062580d395a8c99631c104d6aec250f961152ddMady Mellor    protected boolean handleSlideBack() {
370f062580d395a8c99631c104d6aec250f961152ddMady Mellor        if (mSettingsIconRow != null && mSettingsIconRow.isVisible()) {
371f062580d395a8c99631c104d6aec250f961152ddMady Mellor            animateTranslateNotification(0 /* targetLeft */);
372f062580d395a8c99631c104d6aec250f961152ddMady Mellor            return true;
373f062580d395a8c99631c104d6aec250f961152ddMady Mellor        }
374f062580d395a8c99631c104d6aec250f961152ddMady Mellor        return false;
375f062580d395a8c99631c104d6aec250f961152ddMady Mellor    }
376f062580d395a8c99631c104d6aec250f961152ddMady Mellor
377f062580d395a8c99631c104d6aec250f961152ddMady Mellor    @Override
37834d93b0985063090a9bad88a1b80e1b99bae3332Selim Cinek    protected boolean shouldHideBackground() {
37934d93b0985063090a9bad88a1b80e1b99bae3332Selim Cinek        return super.shouldHideBackground() || mShowNoBackground;
380263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek    }
381263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek
382263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek    @Override
383263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek    public boolean isSummaryWithChildren() {
384263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek        return mIsSummaryWithChildren;
385b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
386b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
387b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    @Override
388b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public boolean areChildrenExpanded() {
389b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        return mChildrenExpanded;
390b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
391b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
392b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public List<ExpandableNotificationRow> getNotificationChildren() {
393b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        return mChildrenContainer == null ? null : mChildrenContainer.getNotificationChildren();
394b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
395b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
396eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek    public int getNumberOfNotificationChildren() {
397eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek        if (mChildrenContainer == null) {
398eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek            return 0;
399eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek        }
400eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek        return mChildrenContainer.getNotificationChildren().size();
401eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek    }
402eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek
403b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    /**
404b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek     * Apply the order given in the list to the children.
405b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek     *
406b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek     * @param childOrder the new list order
407b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek     * @return whether the list order has changed
408b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek     */
409b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public boolean applyChildOrder(List<ExpandableNotificationRow> childOrder) {
410b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        return mChildrenContainer != null && mChildrenContainer.applyChildOrder(childOrder);
411b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
412b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
413b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public void getChildrenStates(StackScrollState resultState) {
41483bc78338437a460076a4b5778ded38440ac3501Selim Cinek        if (mIsSummaryWithChildren) {
415b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            StackViewState parentState = resultState.getViewStateForView(this);
416b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            mChildrenContainer.getState(resultState, parentState);
417b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        }
418b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
419b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
420b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public void applyChildrenState(StackScrollState state) {
42183bc78338437a460076a4b5778ded38440ac3501Selim Cinek        if (mIsSummaryWithChildren) {
422b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            mChildrenContainer.applyState(state);
423b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        }
424b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
425b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
426b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public void prepareExpansionChanged(StackScrollState state) {
42783bc78338437a460076a4b5778ded38440ac3501Selim Cinek        if (mIsSummaryWithChildren) {
428b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            mChildrenContainer.prepareExpansionChanged(state);
429b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        }
430b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
431b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
432b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public void startChildAnimation(StackScrollState finalState,
4339969559da02f54fcbd7832de9810507a581d98d8Selim Cinek            StackStateAnimator stateAnimator, long delay, long duration) {
43483bc78338437a460076a4b5778ded38440ac3501Selim Cinek        if (mIsSummaryWithChildren) {
4359969559da02f54fcbd7832de9810507a581d98d8Selim Cinek            mChildrenContainer.startAnimationToState(finalState, stateAnimator, delay,
436b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek                    duration);
437b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        }
438b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
439b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
440b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public ExpandableNotificationRow getViewAtPosition(float y) {
44143d30f03f45f3f9ad3955f5c83f4d21f26891de6Selim Cinek        if (!mIsSummaryWithChildren || !mChildrenExpanded) {
442b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            return this;
443b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        } else {
444b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            ExpandableNotificationRow view = mChildrenContainer.getViewAtPosition(y);
445b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            return view == null ? this : view;
446b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        }
447b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
448b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
449ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek    public NotificationGuts getGuts() {
450ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek        return mGuts;
451ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek    }
452ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek
453684a442b812a5e95d813700ffa2fd17ca72048a7Selim Cinek    /**
454684a442b812a5e95d813700ffa2fd17ca72048a7Selim Cinek     * Set this notification to be pinned to the top if {@link #isHeadsUp()} is true. By doing this
455684a442b812a5e95d813700ffa2fd17ca72048a7Selim Cinek     * the notification will be rendered on top of the screen.
456684a442b812a5e95d813700ffa2fd17ca72048a7Selim Cinek     *
457684a442b812a5e95d813700ffa2fd17ca72048a7Selim Cinek     * @param pinned whether it is pinned
458684a442b812a5e95d813700ffa2fd17ca72048a7Selim Cinek     */
459684a442b812a5e95d813700ffa2fd17ca72048a7Selim Cinek    public void setPinned(boolean pinned) {
460def35a86530200958384191d43d321dbcda16e2aSelim Cinek        int intrinsicHeight = getIntrinsicHeight();
461684a442b812a5e95d813700ffa2fd17ca72048a7Selim Cinek        mIsPinned = pinned;
462def35a86530200958384191d43d321dbcda16e2aSelim Cinek        if (intrinsicHeight != getIntrinsicHeight()) {
463def35a86530200958384191d43d321dbcda16e2aSelim Cinek            notifyHeightChanged(false);
464def35a86530200958384191d43d321dbcda16e2aSelim Cinek        }
46531aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        if (pinned) {
46631aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek            setIconAnimationRunning(true);
46731aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek            mExpandedWhenPinned = false;
46831aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        } else if (mExpandedWhenPinned) {
46931aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek            setUserExpanded(true);
47031aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        }
47198713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek        setChronometerRunning(mLastChronometerRunning);
472b8f09cf5533d458868a335ce334e4880b2b0788dSelim Cinek    }
473b8f09cf5533d458868a335ce334e4880b2b0788dSelim Cinek
474684a442b812a5e95d813700ffa2fd17ca72048a7Selim Cinek    public boolean isPinned() {
475684a442b812a5e95d813700ffa2fd17ca72048a7Selim Cinek        return mIsPinned;
476b8f09cf5533d458868a335ce334e4880b2b0788dSelim Cinek    }
477b8f09cf5533d458868a335ce334e4880b2b0788dSelim Cinek
47831aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek    /**
47931aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek     * @param atLeastMinHeight should the value returned be at least the minimum height.
48031aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek     *                         Used to avoid cyclic calls
48131aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek     * @return the height of the heads up notification when pinned
48231aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek     */
48331aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek    public int getPinnedHeadsUpHeight(boolean atLeastMinHeight) {
48477019c72332cb31dd1cb713ea4c66e267e6cbf39Selim Cinek        if (mIsSummaryWithChildren) {
48577019c72332cb31dd1cb713ea4c66e267e6cbf39Selim Cinek            return mChildrenContainer.getIntrinsicHeight();
48677019c72332cb31dd1cb713ea4c66e267e6cbf39Selim Cinek        }
48731aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        if(mExpandedWhenPinned) {
48831aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek            return Math.max(getMaxExpandHeight(), mHeadsUpHeight);
48931aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        } else if (atLeastMinHeight) {
490567e845d99840a6e556595739a15e16132eb2f1eSelim Cinek            return Math.max(getCollapsedHeight(), mHeadsUpHeight);
49131aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        } else {
49231aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek            return mHeadsUpHeight;
49331aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        }
494b8f09cf5533d458868a335ce334e4880b2b0788dSelim Cinek    }
495b8f09cf5533d458868a335ce334e4880b2b0788dSelim Cinek
4965eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi    /**
4975eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi     * Mark whether this notification was just clicked, i.e. the user has just clicked this
4985eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi     * notification in this frame.
4995eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi     */
5005eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi    public void setJustClicked(boolean justClicked) {
5015eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi        mJustClicked = justClicked;
5025eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi    }
5035eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi
5045eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi    /**
5055eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi     * @return true if this notification has been clicked in this frame, false otherwise
5065eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi     */
5075eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi    public boolean wasJustClicked() {
5085eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi        return mJustClicked;
5095eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi    }
5105eb67c22489f5fda22770d1fc824e7a8013ec025Jorim Jaggi
51198713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek    public void setChronometerRunning(boolean running) {
51298713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek        mLastChronometerRunning = running;
51398713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek        setChronometerRunning(running, mPrivateLayout);
51498713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek        setChronometerRunning(running, mPublicLayout);
51598713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek        if (mChildrenContainer != null) {
51698713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            List<ExpandableNotificationRow> notificationChildren =
51798713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek                    mChildrenContainer.getNotificationChildren();
51898713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            for (int i = 0; i < notificationChildren.size(); i++) {
51998713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek                ExpandableNotificationRow child = notificationChildren.get(i);
52098713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek                child.setChronometerRunning(running);
52198713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            }
52298713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek        }
52398713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek    }
52498713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek
52598713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek    private void setChronometerRunning(boolean running, NotificationContentView layout) {
52698713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek        if (layout != null) {
52798713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            running = running || isPinned();
52898713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            View contractedChild = layout.getContractedChild();
52998713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            View expandedChild = layout.getExpandedChild();
53098713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            View headsUpChild = layout.getHeadsUpChild();
53198713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            setChronometerRunningForChild(running, contractedChild);
53298713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            setChronometerRunningForChild(running, expandedChild);
53398713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            setChronometerRunningForChild(running, headsUpChild);
53498713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek        }
53598713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek    }
53698713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek
53798713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek    private void setChronometerRunningForChild(boolean running, View child) {
53898713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek        if (child != null) {
53998713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            View chronometer = child.findViewById(com.android.internal.R.id.chronometer);
54098713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            if (chronometer instanceof Chronometer) {
54198713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek                ((Chronometer) chronometer).setStarted(running);
54298713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek            }
54398713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek        }
54498713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek    }
54598713a4fcf1061d3366b333c954fd7b8e9f12841Selim Cinek
546ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek    public NotificationHeaderView getNotificationHeader() {
547ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek        if (mNotificationHeader != null) {
548ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek            return mNotificationHeader;
5498d6440dbaba4310cb517ab2a725d75be1ef934f4Selim Cinek        }
550ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek        return mPrivateLayout.getNotificationHeader();
5518d6440dbaba4310cb517ab2a725d75be1ef934f4Selim Cinek    }
5528d6440dbaba4310cb517ab2a725d75be1ef934f4Selim Cinek
55334eda5ed70863320e41b6860a550ba6a4248c652Selim Cinek    private NotificationHeaderView getVisibleNotificationHeader() {
55434eda5ed70863320e41b6860a550ba6a4248c652Selim Cinek        if (mNotificationHeader != null) {
55534eda5ed70863320e41b6860a550ba6a4248c652Selim Cinek            return mNotificationHeader;
55634eda5ed70863320e41b6860a550ba6a4248c652Selim Cinek        }
55734eda5ed70863320e41b6860a550ba6a4248c652Selim Cinek        return getShowingLayout().getVisibleNotificationHeader();
55834eda5ed70863320e41b6860a550ba6a4248c652Selim Cinek    }
55934eda5ed70863320e41b6860a550ba6a4248c652Selim Cinek
560570981d5f1bcd0e5186cc02655254a0606b6ec14Selim Cinek    public void setOnExpandClickListener(OnExpandClickListener onExpandClickListener) {
561570981d5f1bcd0e5186cc02655254a0606b6ec14Selim Cinek        mOnExpandClickListener = onExpandClickListener;
562570981d5f1bcd0e5186cc02655254a0606b6ec14Selim Cinek    }
563570981d5f1bcd0e5186cc02655254a0606b6ec14Selim Cinek
56431aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek    public void setHeadsUpManager(HeadsUpManager headsUpManager) {
56531aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        mHeadsUpManager = headsUpManager;
56631aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek    }
56731aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek
56801af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek    public void reInflateViews() {
56901af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek        initDimens();
57001af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek        if (mIsSummaryWithChildren) {
57101af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek            removeView(mNotificationHeader);
57201af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek            mNotificationHeader = null;
57301af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek            recreateNotificationHeader();
57401af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek            if (mChildrenContainer != null) {
57501af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek                mChildrenContainer.reInflateViews();
57601af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek            }
57701af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek        }
57801af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek        if (mGuts != null) {
57901af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek            View oldGuts = mGuts;
58001af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek            int index = indexOfChild(oldGuts);
58101af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek            removeView(oldGuts);
58201af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek            mGuts = (NotificationGuts) LayoutInflater.from(mContext).inflate(
58301af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek                    R.layout.notification_guts, this, false);
58401af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek            mGuts.setVisibility(oldGuts.getVisibility());
58501af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek            addView(mGuts, index);
58601af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek        }
5874b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        if (mSettingsIconRow != null) {
5884b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            View oldSettings = mSettingsIconRow;
5894b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            int settingsIndex = indexOfChild(oldSettings);
5904b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            removeView(oldSettings);
5914b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            mSettingsIconRow = (NotificationSettingsIconRow) LayoutInflater.from(mContext).inflate(
5924b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                    R.layout.notification_settings_icon_row, this, false);
5934b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            mSettingsIconRow.setNotificationRowParent(ExpandableNotificationRow.this);
5943fd273e6113fb1b8986314a03ab6d7e90efd0beaMady Mellor            mSettingsIconRow.setAppName(mAppName);
5954b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            mSettingsIconRow.setVisibility(oldSettings.getVisibility());
5964b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            addView(mSettingsIconRow, settingsIndex);
5974b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor
5984b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        }
599de33a4ad5696173942dca363339027c892927e8dSelim Cinek        mPrivateLayout.reInflateViews();
600de33a4ad5696173942dca363339027c892927e8dSelim Cinek        mPublicLayout.reInflateViews();
60101af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek    }
60201af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek
603c317933a91b1d33cc4af9b7c6218b9ce675d05eaSelim Cinek    public void setContentBackground(int customBackgroundColor, boolean animate,
604c317933a91b1d33cc4af9b7c6218b9ce675d05eaSelim Cinek            NotificationContentView notificationContentView) {
605c317933a91b1d33cc4af9b7c6218b9ce675d05eaSelim Cinek        if (getShowingLayout() == notificationContentView) {
606c317933a91b1d33cc4af9b7c6218b9ce675d05eaSelim Cinek            setTintColor(customBackgroundColor, animate);
607c317933a91b1d33cc4af9b7c6218b9ce675d05eaSelim Cinek        }
608c317933a91b1d33cc4af9b7c6218b9ce675d05eaSelim Cinek    }
609c317933a91b1d33cc4af9b7c6218b9ce675d05eaSelim Cinek
6100bd8a4b29bf92a901855d889c53186383dd2c5e7Adrian Roos    public void closeRemoteInput() {
6110bd8a4b29bf92a901855d889c53186383dd2c5e7Adrian Roos        mPrivateLayout.closeRemoteInput();
6120bd8a4b29bf92a901855d889c53186383dd2c5e7Adrian Roos        mPublicLayout.closeRemoteInput();
6130bd8a4b29bf92a901855d889c53186383dd2c5e7Adrian Roos    }
6140bd8a4b29bf92a901855d889c53186383dd2c5e7Adrian Roos
615c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek    /**
616c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek     * Set by how much the single line view should be indented.
617c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek     */
618c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek    public void setSingleLineWidthIndention(int indention) {
619c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek        mPrivateLayout.setSingleLineWidthIndention(indention);
620c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek    }
621c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek
622c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek    public int getNotificationColor() {
6234bb593492ccf560382fac9ae533a7429cec53c94Selim Cinek        return mNotificationColor;
6244bb593492ccf560382fac9ae533a7429cec53c94Selim Cinek    }
6254bb593492ccf560382fac9ae533a7429cec53c94Selim Cinek
6264bb593492ccf560382fac9ae533a7429cec53c94Selim Cinek    private void updateNotificationColor() {
6274bb593492ccf560382fac9ae533a7429cec53c94Selim Cinek        mNotificationColor = NotificationColorUtil.resolveContrastColor(mContext,
6284bb593492ccf560382fac9ae533a7429cec53c94Selim Cinek                getStatusBarNotification().getNotification().color);
629c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek    }
630c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek
631c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek    public HybridNotificationView getSingleLineView() {
632c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek        return mPrivateLayout.getSingleLineView();
633c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek    }
634c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek
635f07d06212b08939809aa4128f153bd5179f81fc7Selim Cinek    public boolean isOnKeyguard() {
636f07d06212b08939809aa4128f153bd5179f81fc7Selim Cinek        return mOnKeyguard;
637f07d06212b08939809aa4128f153bd5179f81fc7Selim Cinek    }
638f07d06212b08939809aa4128f153bd5179f81fc7Selim Cinek
639c1e389dadc234827354b95bac98a9c7146ed301cSelim Cinek    public void removeAllChildren() {
640c1e389dadc234827354b95bac98a9c7146ed301cSelim Cinek        List<ExpandableNotificationRow> notificationChildren
641c1e389dadc234827354b95bac98a9c7146ed301cSelim Cinek                = mChildrenContainer.getNotificationChildren();
642c1e389dadc234827354b95bac98a9c7146ed301cSelim Cinek        ArrayList<ExpandableNotificationRow> clonedList = new ArrayList<>(notificationChildren);
643c1e389dadc234827354b95bac98a9c7146ed301cSelim Cinek        for (int i = 0; i < clonedList.size(); i++) {
644c1e389dadc234827354b95bac98a9c7146ed301cSelim Cinek            ExpandableNotificationRow row = clonedList.get(i);
6453f19f60d654421eee5b35a92129081f08c977629Selim Cinek            if (row.keepInParent()) {
6463f19f60d654421eee5b35a92129081f08c977629Selim Cinek                continue;
6473f19f60d654421eee5b35a92129081f08c977629Selim Cinek            }
648c1e389dadc234827354b95bac98a9c7146ed301cSelim Cinek            mChildrenContainer.removeNotification(row);
649a5703187a9dba418f742fab0874a8f683b0bbb0eSelim Cinek            if (!row.isRemoved()) {
650a5703187a9dba418f742fab0874a8f683b0bbb0eSelim Cinek                mHeaderUtil.restoreNotificationHeader(row);
651a5703187a9dba418f742fab0874a8f683b0bbb0eSelim Cinek            }
652c1e389dadc234827354b95bac98a9c7146ed301cSelim Cinek            row.setIsChildInGroup(false, null);
653c1e389dadc234827354b95bac98a9c7146ed301cSelim Cinek        }
654c1e389dadc234827354b95bac98a9c7146ed301cSelim Cinek        onChildrenCountChanged();
655c1e389dadc234827354b95bac98a9c7146ed301cSelim Cinek    }
656c1e389dadc234827354b95bac98a9c7146ed301cSelim Cinek
6571b2a05eb00746756c4d37ad76d597d909019e56fSelim Cinek    public void setForceUnlocked(boolean forceUnlocked) {
6581b2a05eb00746756c4d37ad76d597d909019e56fSelim Cinek        mForceUnlocked = forceUnlocked;
6591b2a05eb00746756c4d37ad76d597d909019e56fSelim Cinek        if (mIsSummaryWithChildren) {
6601b2a05eb00746756c4d37ad76d597d909019e56fSelim Cinek            List<ExpandableNotificationRow> notificationChildren = getNotificationChildren();
6611b2a05eb00746756c4d37ad76d597d909019e56fSelim Cinek            for (ExpandableNotificationRow child : notificationChildren) {
6621b2a05eb00746756c4d37ad76d597d909019e56fSelim Cinek                child.setForceUnlocked(forceUnlocked);
6631b2a05eb00746756c4d37ad76d597d909019e56fSelim Cinek            }
6641b2a05eb00746756c4d37ad76d597d909019e56fSelim Cinek        }
6651b2a05eb00746756c4d37ad76d597d909019e56fSelim Cinek    }
6661b2a05eb00746756c4d37ad76d597d909019e56fSelim Cinek
6673f19f60d654421eee5b35a92129081f08c977629Selim Cinek    public void setDismissed(boolean dismissed) {
6683f19f60d654421eee5b35a92129081f08c977629Selim Cinek        mDismissed = dismissed;
6693f19f60d654421eee5b35a92129081f08c977629Selim Cinek    }
6703f19f60d654421eee5b35a92129081f08c977629Selim Cinek
6713f19f60d654421eee5b35a92129081f08c977629Selim Cinek    public boolean isDismissed() {
6723f19f60d654421eee5b35a92129081f08c977629Selim Cinek        return mDismissed;
6733f19f60d654421eee5b35a92129081f08c977629Selim Cinek    }
6743f19f60d654421eee5b35a92129081f08c977629Selim Cinek
6753f19f60d654421eee5b35a92129081f08c977629Selim Cinek    public boolean keepInParent() {
6763f19f60d654421eee5b35a92129081f08c977629Selim Cinek        return mKeepInParent;
6773f19f60d654421eee5b35a92129081f08c977629Selim Cinek    }
6783f19f60d654421eee5b35a92129081f08c977629Selim Cinek
6793f19f60d654421eee5b35a92129081f08c977629Selim Cinek    public void setKeepInParent(boolean keepInParent) {
6803f19f60d654421eee5b35a92129081f08c977629Selim Cinek        mKeepInParent = keepInParent;
6813f19f60d654421eee5b35a92129081f08c977629Selim Cinek    }
6823f19f60d654421eee5b35a92129081f08c977629Selim Cinek
6833f19f60d654421eee5b35a92129081f08c977629Selim Cinek    public boolean isRemoved() {
6843f19f60d654421eee5b35a92129081f08c977629Selim Cinek        return mRemoved;
6853f19f60d654421eee5b35a92129081f08c977629Selim Cinek    }
6863f19f60d654421eee5b35a92129081f08c977629Selim Cinek
687d009ab1e2a57648cac9de93912964e2a36ae1762Adrian Roos    public void setRemoved() {
688d009ab1e2a57648cac9de93912964e2a36ae1762Adrian Roos        mRemoved = true;
689d009ab1e2a57648cac9de93912964e2a36ae1762Adrian Roos
690d009ab1e2a57648cac9de93912964e2a36ae1762Adrian Roos        mPrivateLayout.setRemoved();
691d009ab1e2a57648cac9de93912964e2a36ae1762Adrian Roos        if (mChildrenContainer != null) {
692d009ab1e2a57648cac9de93912964e2a36ae1762Adrian Roos            mChildrenContainer.setRemoved();
693d009ab1e2a57648cac9de93912964e2a36ae1762Adrian Roos        }
6943f19f60d654421eee5b35a92129081f08c977629Selim Cinek    }
6953f19f60d654421eee5b35a92129081f08c977629Selim Cinek
696d13956475e97da9de83f6519eab514770118e7afSelim Cinek    public NotificationChildrenContainer getChildrenContainer() {
697d13956475e97da9de83f6519eab514770118e7afSelim Cinek        return mChildrenContainer;
698d13956475e97da9de83f6519eab514770118e7afSelim Cinek    }
699d13956475e97da9de83f6519eab514770118e7afSelim Cinek
70078403d79739605511ea88b653564d81d7bf4bbbaChris Wren    public interface ExpansionLogger {
70178403d79739605511ea88b653564d81d7bf4bbbaChris Wren        public void logNotificationExpansion(String key, boolean userAction, boolean expanded);
70278403d79739605511ea88b653564d81d7bf4bbbaChris Wren    }
7031685e634fb0b14033bd436af8d7174436699ffecSelim Cinek
70451c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    public ExpandableNotificationRow(Context context, AttributeSet attrs) {
70551c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren        super(context, attrs);
7060e2ffbd48bbedf47deb7f6aed96bd07e2fc96f53Blazej Magnowski        mFalsingManager = FalsingManager.getInstance(context);
70701af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek        initDimens();
70801af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek    }
70901af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek
71001af334b70c8ad47c8ce1f465e458863ebe9eae2Selim Cinek    private void initDimens() {
711f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek        mNotificationMinHeightLegacy = getFontScaledHeight(R.dimen.notification_min_height_legacy);
712f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek        mNotificationMinHeight = getFontScaledHeight(R.dimen.notification_min_height);
713f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek        mNotificationMaxHeight = getFontScaledHeight(R.dimen.notification_max_height);
714f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek        mMaxHeadsUpHeightLegacy = getFontScaledHeight(
71577019c72332cb31dd1cb713ea4c66e267e6cbf39Selim Cinek                R.dimen.notification_max_heads_up_height_legacy);
716f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek        mMaxHeadsUpHeight = getFontScaledHeight(R.dimen.notification_max_heads_up_height);
717f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek    }
718f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek
719f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek    /**
720f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek     * @param dimenId the dimen to look up
721f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek     * @return the font scaled dimen as if it were in sp but doesn't shrink sizes below dp
722f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek     */
723f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek    private int getFontScaledHeight(int dimenId) {
724f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek        int dimensionPixelSize = getResources().getDimensionPixelSize(dimenId);
725f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek        float factor = Math.max(1.0f, getResources().getDisplayMetrics().scaledDensity /
726f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek                getResources().getDisplayMetrics().density);
727f619ffccd77c20702d45bd2bd63b626e41b08018Selim Cinek        return (int) (dimensionPixelSize * factor);
72851c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    }
72951c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren
730a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer    /**
731a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer     * Resets this view so it can be re-used for an updated notification.
732a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer     */
73322f2ee567dd1b1a42432251229bcb2f05c1c4700Christoph Studer    @Override
734a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer    public void reset() {
73522f2ee567dd1b1a42432251229bcb2f05c1c4700Christoph Studer        super.reset();
73678403d79739605511ea88b653564d81d7bf4bbbaChris Wren        final boolean wasExpanded = isExpanded();
737a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer        mExpandable = false;
738a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer        mHasUserChangedExpansion = false;
739a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer        mUserLocked = false;
740a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer        mShowingPublic = false;
741ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi        mSensitive = false;
742ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi        mShowingPublicInitialized = false;
743a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer        mIsSystemExpanded = false;
74483bc78338437a460076a4b5778ded38440ac3501Selim Cinek        mOnKeyguard = false;
74551d94917c7dc53845701702bfd63f102a3a2dbc8Selim Cinek        mPublicLayout.reset();
74651d94917c7dc53845701702bfd63f102a3a2dbc8Selim Cinek        mPrivateLayout.reset();
74731094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek        resetHeight();
7484b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        resetTranslation();
74931094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek        logExpansionEvent(false, wasExpanded);
75031094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek    }
75131094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek
75231094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek    public void resetHeight() {
753a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer        mMaxExpandHeight = 0;
7548d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek        mHeadsUpHeight = 0;
75531094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek        onHeightReset();
7566e28a678c7f9fe2cae5a51bfdbab3071a2d8d0baSelim Cinek        requestLayout();
757a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer    }
758a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer
759251957d76e57eb6e5f8068b37346144e10e586a4Jorim Jaggi    @Override
760251957d76e57eb6e5f8068b37346144e10e586a4Jorim Jaggi    protected void onFinishInflate() {
761251957d76e57eb6e5f8068b37346144e10e586a4Jorim Jaggi        super.onFinishInflate();
762be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi        mPublicLayout = (NotificationContentView) findViewById(R.id.expandedPublic);
763fa0a2d3d90fdde14784ec6351a0798bc21c2f126Selim Cinek        mPublicLayout.setContainingNotification(this);
764be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi        mPrivateLayout = (NotificationContentView) findViewById(R.id.expanded);
765eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        mPrivateLayout.setExpandClickListener(mExpandClickListener);
766fa0a2d3d90fdde14784ec6351a0798bc21c2f126Selim Cinek        mPrivateLayout.setContainingNotification(this);
767eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        mPublicLayout.setExpandClickListener(mExpandClickListener);
7684b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        mSettingsIconRowStub = (ViewStub) findViewById(R.id.settings_icon_row_stub);
7694b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        mSettingsIconRowStub.setOnInflateListener(new ViewStub.OnInflateListener() {
7704b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            @Override
7714b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            public void onInflate(ViewStub stub, View inflated) {
7724b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                mSettingsIconRow = (NotificationSettingsIconRow) inflated;
7734b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                mSettingsIconRow.setNotificationRowParent(ExpandableNotificationRow.this);
7743fd273e6113fb1b8986314a03ab6d7e90efd0beaMady Mellor                mSettingsIconRow.setAppName(mAppName);
7754b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            }
7764b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        });
777ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek        mGutsStub = (ViewStub) findViewById(R.id.notification_guts_stub);
778ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek        mGutsStub.setOnInflateListener(new ViewStub.OnInflateListener() {
779b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi            @Override
780b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi            public void onInflate(ViewStub stub, View inflated) {
781b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi                mGuts = (NotificationGuts) inflated;
782b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi                mGuts.setClipTopAmount(getClipTopAmount());
783b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi                mGuts.setActualHeight(getActualHeight());
784ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek                mGutsStub = null;
785b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi            }
786b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi        });
787b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        mChildrenContainerStub = (ViewStub) findViewById(R.id.child_container_stub);
788b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        mChildrenContainerStub.setOnInflateListener(new ViewStub.OnInflateListener() {
789b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
790b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            @Override
791b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            public void onInflate(ViewStub stub, View inflated) {
792b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek                mChildrenContainer = (NotificationChildrenContainer) inflated;
793388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek                mChildrenContainer.setNotificationParent(ExpandableNotificationRow.this);
794c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek                mChildrenContainer.onNotificationUpdated();
7954b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                mTranslateableViews.add(mChildrenContainer);
796b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            }
797b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        });
798863834bd96bdebcf21f4c4a7d8285d4858c061e4Selim Cinek        mVetoButton = findViewById(R.id.veto);
7994b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor
8004b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        // Add the views that we translate to reveal the gear
8014b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        mTranslateableViews = new ArrayList<View>();
8024b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        for (int i = 0; i < getChildCount(); i++) {
8034b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            mTranslateableViews.add(getChildAt(i));
8044b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        }
8054b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        // Remove views that don't translate
8064b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        mTranslateableViews.remove(mVetoButton);
8074b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        mTranslateableViews.remove(mSettingsIconRowStub);
8084b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        mTranslateableViews.remove(mChildrenContainerStub);
8094b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        mTranslateableViews.remove(mGutsStub);
8104b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    }
8114b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor
81234958fa272c9216db4002546c3efad692b3d7775Mady Mellor    private void setTranslationForOutline(float translationX) {
8134b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        setOutlineRect(false, translationX, getTop(), getRight() + translationX, getBottom());
8144b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    }
8154b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor
8164b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    public void resetTranslation() {
8174b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        if (mTranslateableViews != null) {
8184b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            for (int i = 0; i < mTranslateableViews.size(); i++) {
8194b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                mTranslateableViews.get(i).setTranslationX(0);
8204b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            }
8214b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            setTranslationForOutline(0);
8224b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        }
8234b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        if (mSettingsIconRow != null) {
8244b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            mSettingsIconRow.resetState();
8254b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        }
8264b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    }
8274b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor
8284b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    public void animateTranslateNotification(final float leftTarget) {
8294b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        if (mTranslateAnim != null) {
8304b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            mTranslateAnim.cancel();
8314b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        }
83234958fa272c9216db4002546c3efad692b3d7775Mady Mellor        mTranslateAnim = (AnimatorSet) getTranslateViewAnimator(leftTarget,
83334958fa272c9216db4002546c3efad692b3d7775Mady Mellor                null /* updateListener */);
83434958fa272c9216db4002546c3efad692b3d7775Mady Mellor        if (mTranslateAnim != null) {
83534958fa272c9216db4002546c3efad692b3d7775Mady Mellor            mTranslateAnim.start();
83634958fa272c9216db4002546c3efad692b3d7775Mady Mellor        }
83734958fa272c9216db4002546c3efad692b3d7775Mady Mellor    }
83834958fa272c9216db4002546c3efad692b3d7775Mady Mellor
83934958fa272c9216db4002546c3efad692b3d7775Mady Mellor    @Override
84034958fa272c9216db4002546c3efad692b3d7775Mady Mellor    public void setTranslation(float translationX) {
84134958fa272c9216db4002546c3efad692b3d7775Mady Mellor        if (areGutsExposed()) {
84234958fa272c9216db4002546c3efad692b3d7775Mady Mellor            // Don't translate if guts are showing.
84334958fa272c9216db4002546c3efad692b3d7775Mady Mellor            return;
84434958fa272c9216db4002546c3efad692b3d7775Mady Mellor        }
84534958fa272c9216db4002546c3efad692b3d7775Mady Mellor        // Translate the group of views
84634958fa272c9216db4002546c3efad692b3d7775Mady Mellor        for (int i = 0; i < mTranslateableViews.size(); i++) {
84734958fa272c9216db4002546c3efad692b3d7775Mady Mellor            if (mTranslateableViews.get(i) != null) {
84834958fa272c9216db4002546c3efad692b3d7775Mady Mellor                mTranslateableViews.get(i).setTranslationX(translationX);
84934958fa272c9216db4002546c3efad692b3d7775Mady Mellor            }
85034958fa272c9216db4002546c3efad692b3d7775Mady Mellor        }
85134958fa272c9216db4002546c3efad692b3d7775Mady Mellor        setTranslationForOutline(translationX);
85234958fa272c9216db4002546c3efad692b3d7775Mady Mellor        if (mSettingsIconRow != null) {
85334958fa272c9216db4002546c3efad692b3d7775Mady Mellor            mSettingsIconRow.updateSettingsIcons(translationX, getMeasuredWidth());
85434958fa272c9216db4002546c3efad692b3d7775Mady Mellor        }
85534958fa272c9216db4002546c3efad692b3d7775Mady Mellor    }
85634958fa272c9216db4002546c3efad692b3d7775Mady Mellor
85734958fa272c9216db4002546c3efad692b3d7775Mady Mellor    @Override
85834958fa272c9216db4002546c3efad692b3d7775Mady Mellor    public float getTranslation() {
85934958fa272c9216db4002546c3efad692b3d7775Mady Mellor        if (mTranslateableViews != null && mTranslateableViews.size() > 0) {
86034958fa272c9216db4002546c3efad692b3d7775Mady Mellor            // All of the views in the list should have same translation, just use first one.
86134958fa272c9216db4002546c3efad692b3d7775Mady Mellor            return mTranslateableViews.get(0).getTranslationX();
86234958fa272c9216db4002546c3efad692b3d7775Mady Mellor        }
86334958fa272c9216db4002546c3efad692b3d7775Mady Mellor        return 0;
86434958fa272c9216db4002546c3efad692b3d7775Mady Mellor    }
86534958fa272c9216db4002546c3efad692b3d7775Mady Mellor
86634958fa272c9216db4002546c3efad692b3d7775Mady Mellor    public Animator getTranslateViewAnimator(final float leftTarget,
86734958fa272c9216db4002546c3efad692b3d7775Mady Mellor            AnimatorUpdateListener listener) {
868723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor        if (mTranslateAnim != null) {
869723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor            mTranslateAnim.cancel();
870723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor        }
87134958fa272c9216db4002546c3efad692b3d7775Mady Mellor        if (areGutsExposed()) {
87234958fa272c9216db4002546c3efad692b3d7775Mady Mellor            // No translation if guts are exposed.
87334958fa272c9216db4002546c3efad692b3d7775Mady Mellor            return null;
87434958fa272c9216db4002546c3efad692b3d7775Mady Mellor        }
8754b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        AnimatorSet set = new AnimatorSet();
8764b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        if (mTranslateableViews != null) {
8774b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            for (int i = 0; i < mTranslateableViews.size(); i++) {
8784b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                final View animView = mTranslateableViews.get(i);
8794b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                final ObjectAnimator translateAnim = ObjectAnimator.ofFloat(
8804b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                        animView, "translationX", leftTarget);
8814b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                if (i == 0) {
8824b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                    translateAnim.addUpdateListener(new AnimatorUpdateListener() {
8834b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                        @Override
8844b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                        public void onAnimationUpdate(ValueAnimator animation) {
8854b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                            setTranslationForOutline((float) animation.getAnimatedValue());
88634958fa272c9216db4002546c3efad692b3d7775Mady Mellor                            if (mSettingsIconRow != null) {
88734958fa272c9216db4002546c3efad692b3d7775Mady Mellor                                mSettingsIconRow.updateSettingsIcons(
88834958fa272c9216db4002546c3efad692b3d7775Mady Mellor                                        (float) animation.getAnimatedValue(), getMeasuredWidth());
88934958fa272c9216db4002546c3efad692b3d7775Mady Mellor                            }
8904b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                        }
8914b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                    });
89234958fa272c9216db4002546c3efad692b3d7775Mady Mellor                    if (listener != null) {
89334958fa272c9216db4002546c3efad692b3d7775Mady Mellor                        translateAnim.addUpdateListener(listener);
89434958fa272c9216db4002546c3efad692b3d7775Mady Mellor                    }
895723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                    translateAnim.addListener(new AnimatorListenerAdapter() {
896723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                        boolean cancelled = false;
897723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor
898723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                        @Override
899723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                        public void onAnimationCancel(Animator anim) {
900723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                            cancelled = true;
9014b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                        }
902723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor
903723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                        @Override
904723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                        public void onAnimationEnd(Animator anim) {
905723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                            if (!cancelled && mSettingsIconRow != null && leftTarget == 0) {
906723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                                mSettingsIconRow.resetState();
907723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                                mTranslateAnim = null;
908723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                            }
909723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                        }
910723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                    });
911723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor                }
9124b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                set.play(translateAnim);
9134b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            }
9144b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        }
915723f1f996fd78f08e5e91ed57420bd431e11f903Mady Mellor        mTranslateAnim = set;
91634958fa272c9216db4002546c3efad692b3d7775Mady Mellor        return set;
9174b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    }
9184b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor
9194b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    public float getSpaceForGear() {
9204b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        if (mSettingsIconRow != null) {
9214b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            return mSettingsIconRow.getSpaceForGear();
9224b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        }
9234b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        return 0;
9244b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    }
9254b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor
9264b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    public NotificationSettingsIconRow getSettingsRow() {
9274b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        if (mSettingsIconRow == null) {
9284b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            mSettingsIconRowStub.inflate();
9294b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        }
9304b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor        return mSettingsIconRow;
9314b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor    }
9324b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor
933ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek    public void inflateGuts() {
934ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek        if (mGuts == null) {
935ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek            mGutsStub.inflate();
936ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek        }
937ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek    }
938ab29aebf00a0ebd286a92d129f35c182b6888f3bSelim Cinek
939da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek    private void updateChildrenVisibility() {
940d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        mPrivateLayout.setVisibility(!mShowingPublic && !mIsSummaryWithChildren ? VISIBLE
941d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                : INVISIBLE);
942ef5127ea5f34f7a4c961021f6b691174bcb81d2eSelim Cinek        if (mChildrenContainer != null) {
943ef5127ea5f34f7a4c961021f6b691174bcb81d2eSelim Cinek            mChildrenContainer.setVisibility(!mShowingPublic && mIsSummaryWithChildren ? VISIBLE
944ef5127ea5f34f7a4c961021f6b691174bcb81d2eSelim Cinek                    : INVISIBLE);
945ef5127ea5f34f7a4c961021f6b691174bcb81d2eSelim Cinek        }
946ef5127ea5f34f7a4c961021f6b691174bcb81d2eSelim Cinek        if (mNotificationHeader != null) {
947ef5127ea5f34f7a4c961021f6b691174bcb81d2eSelim Cinek            mNotificationHeader.setVisibility(!mShowingPublic && mIsSummaryWithChildren ? VISIBLE
948ef5127ea5f34f7a4c961021f6b691174bcb81d2eSelim Cinek                    : INVISIBLE);
949b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        }
950da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek        // The limits might have changed if the view suddenly became a group or vice versa
951da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek        updateLimits();
952b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
953b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
954fe40f7d13bfc1faa35c9a131ce4be5104cb8f6b9Jorim Jaggi    @Override
955a54956a0bc611b1e9b3914edc7a604b59688f6b7Alan Viverette    public boolean onRequestSendAccessibilityEventInternal(View child, AccessibilityEvent event) {
956a54956a0bc611b1e9b3914edc7a604b59688f6b7Alan Viverette        if (super.onRequestSendAccessibilityEventInternal(child, event)) {
957fe40f7d13bfc1faa35c9a131ce4be5104cb8f6b9Jorim Jaggi            // Add a record for the entire layout since its content is somehow small.
958fe40f7d13bfc1faa35c9a131ce4be5104cb8f6b9Jorim Jaggi            // The event comes from a leaf view that is interacted with.
959fe40f7d13bfc1faa35c9a131ce4be5104cb8f6b9Jorim Jaggi            AccessibilityEvent record = AccessibilityEvent.obtain();
960fe40f7d13bfc1faa35c9a131ce4be5104cb8f6b9Jorim Jaggi            onInitializeAccessibilityEvent(record);
961fe40f7d13bfc1faa35c9a131ce4be5104cb8f6b9Jorim Jaggi            dispatchPopulateAccessibilityEvent(record);
962fe40f7d13bfc1faa35c9a131ce4be5104cb8f6b9Jorim Jaggi            event.appendRecord(record);
963fe40f7d13bfc1faa35c9a131ce4be5104cb8f6b9Jorim Jaggi            return true;
964fe40f7d13bfc1faa35c9a131ce4be5104cb8f6b9Jorim Jaggi        }
965fe40f7d13bfc1faa35c9a131ce4be5104cb8f6b9Jorim Jaggi        return false;
966c5dc0d0cce373fbf292e13633c114a431d747167Jorim Jaggi    }
96751c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren
968e15452bb49d2531eee3086acb4763dd125f8053aJohn Spurlock    @Override
9694e857f4ef0357e05806819d0488a73a12208fe8fJorim Jaggi    public void setDark(boolean dark, boolean fade, long delay) {
9704e857f4ef0357e05806819d0488a73a12208fe8fJorim Jaggi        super.setDark(dark, fade, delay);
971e15452bb49d2531eee3086acb4763dd125f8053aJohn Spurlock        final NotificationContentView showing = getShowingLayout();
972e15452bb49d2531eee3086acb4763dd125f8053aJohn Spurlock        if (showing != null) {
9734e857f4ef0357e05806819d0488a73a12208fe8fJorim Jaggi            showing.setDark(dark, fade, delay);
974e15452bb49d2531eee3086acb4763dd125f8053aJohn Spurlock        }
9759c7712d45ccec56a80873a83e56a83f810624b43Selim Cinek        if (mIsSummaryWithChildren) {
976c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek            mChildrenContainer.setDark(dark, fade, delay);
9779c7712d45ccec56a80873a83e56a83f810624b43Selim Cinek            mNotificationHeaderWrapper.setDark(dark, fade, delay);
9789c7712d45ccec56a80873a83e56a83f810624b43Selim Cinek        }
979e15452bb49d2531eee3086acb4763dd125f8053aJohn Spurlock    }
980e15452bb49d2531eee3086acb4763dd125f8053aJohn Spurlock
98151c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    public boolean isExpandable() {
982388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek        if (mIsSummaryWithChildren && !mShowingPublic) {
983388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek            return !mChildrenExpanded;
984388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek        }
98551c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren        return mExpandable;
98651c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    }
98751c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren
98851c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    public void setExpandable(boolean expandable) {
98951c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren        mExpandable = expandable;
990eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        mPrivateLayout.updateExpandButtons(isExpandable());
99151c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    }
99251c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren
9934ffd63611a0d516c9988b37e9c06e6f8390c2a2fSelim Cinek    @Override
9944ffd63611a0d516c9988b37e9c06e6f8390c2a2fSelim Cinek    public void setClipToActualHeight(boolean clipToActualHeight) {
995084c16b8b380e7ff0d38d9e2846db321f0214931Selim Cinek        super.setClipToActualHeight(clipToActualHeight || isUserLocked());
996084c16b8b380e7ff0d38d9e2846db321f0214931Selim Cinek        getShowingLayout().setClipToActualHeight(clipToActualHeight || isUserLocked());
9974ffd63611a0d516c9988b37e9c06e6f8390c2a2fSelim Cinek    }
9984ffd63611a0d516c9988b37e9c06e6f8390c2a2fSelim Cinek
9991685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    /**
10001685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * @return whether the user has changed the expansion state
10011685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     */
10021685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    public boolean hasUserChangedExpansion() {
10031685e634fb0b14033bd436af8d7174436699ffecSelim Cinek        return mHasUserChangedExpansion;
10041685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    }
10051685e634fb0b14033bd436af8d7174436699ffecSelim Cinek
100651c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    public boolean isUserExpanded() {
100751c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren        return mUserExpanded;
100851c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    }
100951c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren
10101685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    /**
10111685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * Set this notification to be expanded by the user
10121685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     *
10131685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * @param userExpanded whether the user wants this notification to be expanded
10141685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     */
101551c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    public void setUserExpanded(boolean userExpanded) {
1016388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek        setUserExpanded(userExpanded, false /* allowChildExpansion */);
1017388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek    }
1018388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek
1019388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek    /**
1020388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek     * Set this notification to be expanded by the user
1021388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek     *
1022388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek     * @param userExpanded whether the user wants this notification to be expanded
1023388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek     * @param allowChildExpansion whether a call to this method allows expanding children
1024388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek     */
1025388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek    public void setUserExpanded(boolean userExpanded, boolean allowChildExpansion) {
10260e2ffbd48bbedf47deb7f6aed96bd07e2fc96f53Blazej Magnowski        mFalsingManager.setNotificationExpanded();
1027388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek        if (mIsSummaryWithChildren && !mShowingPublic && allowChildExpansion) {
1028388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek            mGroupManager.setGroupExpanded(mStatusBarNotification, userExpanded);
1029388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek            return;
1030388df6dd3d07376ecd7446cae36e1486cd313171Selim Cinek        }
1031a7fe63190cc3f95af1830886edd80acef0c334e3Christoph Studer        if (userExpanded && !mExpandable) return;
103278403d79739605511ea88b653564d81d7bf4bbbaChris Wren        final boolean wasExpanded = isExpanded();
10331685e634fb0b14033bd436af8d7174436699ffecSelim Cinek        mHasUserChangedExpansion = true;
103451c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren        mUserExpanded = userExpanded;
103578403d79739605511ea88b653564d81d7bf4bbbaChris Wren        logExpansionEvent(true, wasExpanded);
103651c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    }
103751c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren
1038ccd14fbcfe613eae71f0e00c39f38e5125749389Selim Cinek    public void resetUserExpansion() {
1039ccd14fbcfe613eae71f0e00c39f38e5125749389Selim Cinek        mHasUserChangedExpansion = false;
1040ccd14fbcfe613eae71f0e00c39f38e5125749389Selim Cinek        mUserExpanded = false;
1041ccd14fbcfe613eae71f0e00c39f38e5125749389Selim Cinek    }
1042ccd14fbcfe613eae71f0e00c39f38e5125749389Selim Cinek
104351c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    public boolean isUserLocked() {
10441b2a05eb00746756c4d37ad76d597d909019e56fSelim Cinek        return mUserLocked && !mForceUnlocked;
104551c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    }
104651c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren
104751c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    public void setUserLocked(boolean userLocked) {
104851c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren        mUserLocked = userLocked;
10498f2f6a67fad7aed720e33a6629cb65d368ebfb80Selim Cinek        mPrivateLayout.setUserExpanding(userLocked);
105042357e030c095867b95e2e8a718649587c5ebf52Selim Cinek        if (mIsSummaryWithChildren) {
105142357e030c095867b95e2e8a718649587c5ebf52Selim Cinek            mChildrenContainer.setUserLocked(userLocked);
105242357e030c095867b95e2e8a718649587c5ebf52Selim Cinek        }
105351c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren    }
105451c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren
10551685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    /**
10561685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * @return has the system set this notification to be expanded
10571685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     */
10581685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    public boolean isSystemExpanded() {
10591685e634fb0b14033bd436af8d7174436699ffecSelim Cinek        return mIsSystemExpanded;
10601685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    }
10611685e634fb0b14033bd436af8d7174436699ffecSelim Cinek
10621685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    /**
10631685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * Set this notification to be expanded by the system.
10641685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     *
10651685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * @param expand whether the system wants this notification to be expanded.
10661685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     */
10671685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    public void setSystemExpanded(boolean expand) {
106831094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek        if (expand != mIsSystemExpanded) {
106931094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek            final boolean wasExpanded = isExpanded();
107031094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek            mIsSystemExpanded = expand;
1071b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            notifyHeightChanged(false /* needsAnimation */);
107231094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek            logExpansionEvent(false, wasExpanded);
1073c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek            if (mChildrenContainer != null) {
1074c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek                mChildrenContainer.updateGroupOverflow();
1075c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek            }
107631094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek        }
1077dce3c4cca5d4df4cc49c1a9f0537e2fecdbc45d2Jorim Jaggi    }
1078dce3c4cca5d4df4cc49c1a9f0537e2fecdbc45d2Jorim Jaggi
1079dce3c4cca5d4df4cc49c1a9f0537e2fecdbc45d2Jorim Jaggi    /**
108083bc78338437a460076a4b5778ded38440ac3501Selim Cinek     * @param onKeyguard whether to prevent notification expansion
1081dce3c4cca5d4df4cc49c1a9f0537e2fecdbc45d2Jorim Jaggi     */
108283bc78338437a460076a4b5778ded38440ac3501Selim Cinek    public void setOnKeyguard(boolean onKeyguard) {
108383bc78338437a460076a4b5778ded38440ac3501Selim Cinek        if (onKeyguard != mOnKeyguard) {
108431094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek            final boolean wasExpanded = isExpanded();
108583bc78338437a460076a4b5778ded38440ac3501Selim Cinek            mOnKeyguard = onKeyguard;
108631094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek            logExpansionEvent(false, wasExpanded);
108731094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek            if (wasExpanded != isExpanded()) {
1088c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek                if (mIsSummaryWithChildren) {
1089c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek                    mChildrenContainer.updateGroupOverflow();
1090c897bd3e91ed442b0f32c3a5b9918e9e580b62b1Selim Cinek                }
10914b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor                notifyHeightChanged(false /* needsAnimation */);
109231094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek            }
109331094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek        }
10941685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    }
10951685e634fb0b14033bd436af8d7174436699ffecSelim Cinek
10961685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    /**
10970d3e62f3e07a69f21c1b1dfa2c8c0fb8b6c95655Dan Sandler     * @return Can the underlying notification be cleared?
10980d3e62f3e07a69f21c1b1dfa2c8c0fb8b6c95655Dan Sandler     */
10990d3e62f3e07a69f21c1b1dfa2c8c0fb8b6c95655Dan Sandler    public boolean isClearable() {
1100a37774f098a5204947ff4b4787c4b753bb9016dbSelim Cinek        return mStatusBarNotification != null && mStatusBarNotification.isClearable();
11010d3e62f3e07a69f21c1b1dfa2c8c0fb8b6c95655Dan Sandler    }
11020d3e62f3e07a69f21c1b1dfa2c8c0fb8b6c95655Dan Sandler
11039cbadd3c08a7d7dd3412743dd04aecb16c5a1595Jorim Jaggi    @Override
11049cbadd3c08a7d7dd3412743dd04aecb16c5a1595Jorim Jaggi    public int getIntrinsicHeight() {
1105be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi        if (isUserLocked()) {
1106be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi            return getActualHeight();
1107be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi        }
1108d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        if (mGuts != null && mGuts.areGutsExposed()) {
1109d84a5930cca7add37e7e23305538d29959daf199Selim Cinek            return mGuts.getHeight();
1110d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        } else if ((isChildInGroup() && !isGroupExpanded())) {
1111d84a5930cca7add37e7e23305538d29959daf199Selim Cinek            return mPrivateLayout.getMinHeight();
1112d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        } else if (mSensitive && mHideSensitiveForIntrinsicHeight) {
1113d84a5930cca7add37e7e23305538d29959daf199Selim Cinek            return getMinHeight();
111483bc78338437a460076a4b5778ded38440ac3501Selim Cinek        } else if (mIsSummaryWithChildren && !mOnKeyguard) {
1115eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek            return mChildrenContainer.getIntrinsicHeight();
111660122be6747c4f79b96f6808158f8f7e7548b7d3Selim Cinek        } else if (mIsHeadsUp) {
111731aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek            if (isPinned()) {
111831aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek                return getPinnedHeadsUpHeight(true /* atLeastMinHeight */);
111931aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek            } else if (isExpanded()) {
1120d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                return Math.max(getMaxExpandHeight(), mHeadsUpHeight);
11218d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek            } else {
1122567e845d99840a6e556595739a15e16132eb2f1eSelim Cinek                return Math.max(getCollapsedHeight(), mHeadsUpHeight);
11238d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek            }
112431aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        } else if (isExpanded()) {
112583bc78338437a460076a4b5778ded38440ac3501Selim Cinek            return getMaxExpandHeight();
1126d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        } else {
1127567e845d99840a6e556595739a15e16132eb2f1eSelim Cinek            return getCollapsedHeight();
11281685e634fb0b14033bd436af8d7174436699ffecSelim Cinek        }
1129b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
11301685e634fb0b14033bd436af8d7174436699ffecSelim Cinek
1131eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek    private boolean isGroupExpanded() {
1132eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek        return mGroupManager.isGroupExpanded(mStatusBarNotification);
1133b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
1134b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
1135eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek    /**
1136eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek     * @return whether this view has a header on the top of the content
1137eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek     */
1138eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek    private boolean hasNotificationHeader() {
1139eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek        return mIsSummaryWithChildren;
11401685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    }
11411685e634fb0b14033bd436af8d7174436699ffecSelim Cinek
1142263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek    private void onChildrenCountChanged() {
11438fc93c90839e5d9dd52bca9dd97c198c0fe68af1Selim Cinek        mIsSummaryWithChildren = BaseStatusBar.ENABLE_CHILD_NOTIFICATIONS
11442a7393410b6390831143dca198438a4e58bdf88aSelim Cinek                && mChildrenContainer != null && mChildrenContainer.getChildCount() > 0;
11458fc93c90839e5d9dd52bca9dd97c198c0fe68af1Selim Cinek        if (mIsSummaryWithChildren) {
11468fc93c90839e5d9dd52bca9dd97c198c0fe68af1Selim Cinek            if (mNotificationHeader == null) {
1147eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek                recreateNotificationHeader();
1148eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek            }
1149263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek        }
1150eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        mPrivateLayout.updateExpandButtons(isExpandable());
1151ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek        updateChildrenHeaderAppearance();
1152da42d65ea5a0eec7d1eaf48fee19ead419994b16Selim Cinek        updateChildrenVisibility();
1153263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek    }
1154263398f0175efc8bc8c965473f9565a693a0a0e0Selim Cinek
11551685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    /**
11561685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * Check whether the view state is currently expanded. This is given by the system in {@link
11571685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * #setSystemExpanded(boolean)} and can be overridden by user expansion or
11581685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * collapsing in {@link #setUserExpanded(boolean)}. Note that the visual appearance of this
11591685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * view can differ from this state, if layout params are modified from outside.
11601685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     *
11611685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     * @return whether the view state is currently expanded.
11621685e634fb0b14033bd436af8d7174436699ffecSelim Cinek     */
116383bc78338437a460076a4b5778ded38440ac3501Selim Cinek    public boolean isExpanded() {
1164e81b82ba252582753cb87ba424c82028b6e490ecSelim Cinek        return isExpanded(false /* allowOnKeyguard */);
1165e81b82ba252582753cb87ba424c82028b6e490ecSelim Cinek    }
1166e81b82ba252582753cb87ba424c82028b6e490ecSelim Cinek
1167e81b82ba252582753cb87ba424c82028b6e490ecSelim Cinek    public boolean isExpanded(boolean allowOnKeyguard) {
1168e81b82ba252582753cb87ba424c82028b6e490ecSelim Cinek        return (!mOnKeyguard || allowOnKeyguard)
1169b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek                && (!hasUserChangedExpansion() && (isSystemExpanded() || isSystemChildExpanded())
1170b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek                || isUserExpanded());
1171b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
1172b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
1173b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    private boolean isSystemChildExpanded() {
1174b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        return mIsSystemChildExpanded;
1175b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
1176b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
1177b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public void setSystemChildExpanded(boolean expanded) {
1178b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        mIsSystemChildExpanded = expanded;
11791685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    }
11801685e634fb0b14033bd436af8d7174436699ffecSelim Cinek
11811685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    @Override
11821685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
11831685e634fb0b14033bd436af8d7174436699ffecSelim Cinek        super.onLayout(changed, left, top, right, bottom);
11848d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek        updateMaxHeights();
1185a6edc878293e49594a6aac7a0d0e41c7980ece07Mady Mellor        if (mSettingsIconRow != null) {
1186a6edc878293e49594a6aac7a0d0e41c7980ece07Mady Mellor            mSettingsIconRow.updateVerticalLocation();
1187a6edc878293e49594a6aac7a0d0e41c7980ece07Mady Mellor        }
11881685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    }
11891685e634fb0b14033bd436af8d7174436699ffecSelim Cinek
11908d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek    private void updateMaxHeights() {
1191d2319fbe6a53ac4c38ca02e4d8e32da86ed0994bSelim Cinek        int intrinsicBefore = getIntrinsicHeight();
11928d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek        View expandedChild = mPrivateLayout.getExpandedChild();
11938d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek        if (expandedChild == null) {
11948d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek            expandedChild = mPrivateLayout.getContractedChild();
11958d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek        }
11968d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek        mMaxExpandHeight = expandedChild.getHeight();
11978d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek        View headsUpChild = mPrivateLayout.getHeadsUpChild();
11981f3f544f21cab3728f749ab66cd6859e9dfcf389Selim Cinek        if (headsUpChild == null) {
11991f3f544f21cab3728f749ab66cd6859e9dfcf389Selim Cinek            headsUpChild = mPrivateLayout.getContractedChild();
12008d490d427c0b0cc321ae61987bb3cfc1c23ff930Selim Cinek        }
12011f3f544f21cab3728f749ab66cd6859e9dfcf389Selim Cinek        mHeadsUpHeight = headsUpChild.getHeight();
1202d2319fbe6a53ac4c38ca02e4d8e32da86ed0994bSelim Cinek        if (intrinsicBefore != getIntrinsicHeight()) {
1203b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            notifyHeightChanged(false  /* needsAnimation */);
1204d2319fbe6a53ac4c38ca02e4d8e32da86ed0994bSelim Cinek        }
1205d2319fbe6a53ac4c38ca02e4d8e32da86ed0994bSelim Cinek    }
1206d2319fbe6a53ac4c38ca02e4d8e32da86ed0994bSelim Cinek
1207fa0a2d3d90fdde14784ec6351a0798bc21c2f126Selim Cinek    @Override
1208fa0a2d3d90fdde14784ec6351a0798bc21c2f126Selim Cinek    public void notifyHeightChanged(boolean needsAnimation) {
1209fa0a2d3d90fdde14784ec6351a0798bc21c2f126Selim Cinek        super.notifyHeightChanged(needsAnimation);
1210fa0a2d3d90fdde14784ec6351a0798bc21c2f126Selim Cinek        getShowingLayout().requestSelectLayout(needsAnimation || isUserLocked());
1211fa0a2d3d90fdde14784ec6351a0798bc21c2f126Selim Cinek    }
1212fa0a2d3d90fdde14784ec6351a0798bc21c2f126Selim Cinek
12133c76d509d362cf5086a63722ab41e04f5d539182Selim Cinek    public void setSensitive(boolean sensitive, boolean hideSensitive) {
1214ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi        mSensitive = sensitive;
12153c76d509d362cf5086a63722ab41e04f5d539182Selim Cinek        mSensitiveHiddenInGeneral = hideSensitive;
1216ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi    }
1217ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi
1218ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi    public void setHideSensitiveForIntrinsicHeight(boolean hideSensitive) {
121960122be6747c4f79b96f6808158f8f7e7548b7d3Selim Cinek        mHideSensitiveForIntrinsicHeight = hideSensitive;
1220a52f6a17efa944adc945a61788cc3beb54c569e7Selim Cinek        if (mIsSummaryWithChildren) {
1221a52f6a17efa944adc945a61788cc3beb54c569e7Selim Cinek            List<ExpandableNotificationRow> notificationChildren =
1222a52f6a17efa944adc945a61788cc3beb54c569e7Selim Cinek                    mChildrenContainer.getNotificationChildren();
1223a52f6a17efa944adc945a61788cc3beb54c569e7Selim Cinek            for (int i = 0; i < notificationChildren.size(); i++) {
1224a52f6a17efa944adc945a61788cc3beb54c569e7Selim Cinek                ExpandableNotificationRow child = notificationChildren.get(i);
1225a52f6a17efa944adc945a61788cc3beb54c569e7Selim Cinek                child.setHideSensitiveForIntrinsicHeight(hideSensitive);
1226a52f6a17efa944adc945a61788cc3beb54c569e7Selim Cinek            }
1227a52f6a17efa944adc945a61788cc3beb54c569e7Selim Cinek        }
1228ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi    }
1229ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi
1230ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi    public void setHideSensitive(boolean hideSensitive, boolean animated, long delay,
1231ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi            long duration) {
1232ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi        boolean oldShowingPublic = mShowingPublic;
1233ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi        mShowingPublic = mSensitive && hideSensitive;
1234ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi        if (mShowingPublicInitialized && mShowingPublic == oldShowingPublic) {
1235ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi            return;
1236ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi        }
1237a5e0f415d351ad1a9c0ffde8d93df91a2384591fDan Sandler
1238a5e0f415d351ad1a9c0ffde8d93df91a2384591fDan Sandler        // bail out if no public version
12391685e634fb0b14033bd436af8d7174436699ffecSelim Cinek        if (mPublicLayout.getChildCount() == 0) return;
1240a5e0f415d351ad1a9c0ffde8d93df91a2384591fDan Sandler
1241ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi        if (!animated) {
1242ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi            mPublicLayout.animate().cancel();
1243ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi            mPrivateLayout.animate().cancel();
1244ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi            mPublicLayout.setAlpha(1f);
1245ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi            mPrivateLayout.setAlpha(1f);
1246ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi            mPublicLayout.setVisibility(mShowingPublic ? View.VISIBLE : View.INVISIBLE);
1247d84a5930cca7add37e7e23305538d29959daf199Selim Cinek            updateChildrenVisibility();
1248ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi        } else {
1249ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi            animateShowingPublic(delay, duration);
1250ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi        }
1251c317933a91b1d33cc4af9b7c6218b9ce675d05eaSelim Cinek        NotificationContentView showingLayout = getShowingLayout();
1252c317933a91b1d33cc4af9b7c6218b9ce675d05eaSelim Cinek        showingLayout.updateBackgroundColor(animated);
1253eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        mPrivateLayout.updateExpandButtons(isExpandable());
1254757d879966fdbff1b67c9ec6fd4b6c75152b991aSelim Cinek        updateClearability();
1255ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi        mShowingPublicInitialized = true;
1256ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi    }
1257ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi
1258ae44128776410abd11bd06ae700db9cc4606a773Jorim Jaggi    private void animateShowingPublic(long delay, long duration) {
1259d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        View[] privateViews = mIsSummaryWithChildren ?
1260d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                new View[] {mChildrenContainer, mNotificationHeader}
1261d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                : new View[] {mPrivateLayout};
1262d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        View[] publicViews = new View[] {mPublicLayout};
1263d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        View[] hiddenChildren = mShowingPublic ? privateViews : publicViews;
1264d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        View[] shownChildren = mShowingPublic ? publicViews : privateViews;
1265d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        for (final View hiddenView : hiddenChildren) {
1266d84a5930cca7add37e7e23305538d29959daf199Selim Cinek            hiddenView.setVisibility(View.VISIBLE);
1267d84a5930cca7add37e7e23305538d29959daf199Selim Cinek            hiddenView.animate().cancel();
1268d84a5930cca7add37e7e23305538d29959daf199Selim Cinek            hiddenView.animate()
1269d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                    .alpha(0f)
1270d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                    .setStartDelay(delay)
1271d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                    .setDuration(duration)
1272d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                    .withEndAction(new Runnable() {
1273d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                        @Override
1274d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                        public void run() {
1275d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                            hiddenView.setVisibility(View.INVISIBLE);
1276d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                        }
1277d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                    });
1278d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        }
1279d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        for (View showView : shownChildren) {
1280d84a5930cca7add37e7e23305538d29959daf199Selim Cinek            showView.setVisibility(View.VISIBLE);
1281d84a5930cca7add37e7e23305538d29959daf199Selim Cinek            showView.setAlpha(0f);
1282d84a5930cca7add37e7e23305538d29959daf199Selim Cinek            showView.animate().cancel();
1283d84a5930cca7add37e7e23305538d29959daf199Selim Cinek            showView.animate()
1284d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                    .alpha(1f)
1285d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                    .setStartDelay(delay)
1286d84a5930cca7add37e7e23305538d29959daf199Selim Cinek                    .setDuration(duration);
1287d84a5930cca7add37e7e23305538d29959daf199Selim Cinek        }
12880d3e62f3e07a69f21c1b1dfa2c8c0fb8b6c95655Dan Sandler    }
12890d3e62f3e07a69f21c1b1dfa2c8c0fb8b6c95655Dan Sandler
12903776fe007550451bb237c705d333247eab2a291cSelim Cinek    public boolean mustStayOnScreen() {
12913776fe007550451bb237c705d333247eab2a291cSelim Cinek        return mIsHeadsUp;
12923776fe007550451bb237c705d333247eab2a291cSelim Cinek    }
12933776fe007550451bb237c705d333247eab2a291cSelim Cinek
1294757d879966fdbff1b67c9ec6fd4b6c75152b991aSelim Cinek    private void updateClearability() {
12950d3e62f3e07a69f21c1b1dfa2c8c0fb8b6c95655Dan Sandler        // public versions cannot be dismissed
12963c76d509d362cf5086a63722ab41e04f5d539182Selim Cinek        mVetoButton.setVisibility(isClearable() && (!mShowingPublic
12973c76d509d362cf5086a63722ab41e04f5d539182Selim Cinek                || !mSensitiveHiddenInGeneral) ? View.VISIBLE : View.GONE);
1298a5e0f415d351ad1a9c0ffde8d93df91a2384591fDan Sandler    }
1299251957d76e57eb6e5f8068b37346144e10e586a4Jorim Jaggi
1300cd35def3c35f04d7fd056590d4668b5ebbc80490Ricky Wai    public void makeActionsVisibile() {
1301cd35def3c35f04d7fd056590d4668b5ebbc80490Ricky Wai        setUserExpanded(true, true);
1302cd35def3c35f04d7fd056590d4668b5ebbc80490Ricky Wai        if (isChildInGroup()) {
1303cd35def3c35f04d7fd056590d4668b5ebbc80490Ricky Wai            mGroupManager.setGroupExpanded(mStatusBarNotification, true);
1304cd35def3c35f04d7fd056590d4668b5ebbc80490Ricky Wai        }
1305cd35def3c35f04d7fd056590d4668b5ebbc80490Ricky Wai        notifyHeightChanged(false);
1306cd35def3c35f04d7fd056590d4668b5ebbc80490Ricky Wai    }
1307cd35def3c35f04d7fd056590d4668b5ebbc80490Ricky Wai
1308b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public void setChildrenExpanded(boolean expanded, boolean animate) {
1309b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        mChildrenExpanded = expanded;
13107b83639c34cb8b52f915099973e0892c5fbfd674Selim Cinek        if (mNotificationHeader != null) {
13117b83639c34cb8b52f915099973e0892c5fbfd674Selim Cinek            mNotificationHeader.setExpanded(expanded);
13127b83639c34cb8b52f915099973e0892c5fbfd674Selim Cinek        }
131383bc78338437a460076a4b5778ded38440ac3501Selim Cinek        if (mChildrenContainer != null) {
131483bc78338437a460076a4b5778ded38440ac3501Selim Cinek            mChildrenContainer.setChildrenExpanded(expanded);
131583bc78338437a460076a4b5778ded38440ac3501Selim Cinek        }
1316b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
1317b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
1318b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public static void applyTint(View v, int color) {
1319b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        int alpha;
1320b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        if (color != 0) {
1321b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            alpha = COLORED_DIVIDER_ALPHA;
1322b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        } else {
1323b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            color = 0xff000000;
1324b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            alpha = DEFAULT_DIVIDER_ALPHA;
1325b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        }
1326b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        if (v.getBackground() instanceof ColorDrawable) {
1327b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            ColorDrawable background = (ColorDrawable) v.getBackground();
1328b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            background.mutate();
1329b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            background.setColor(color);
1330b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek            background.setAlpha(alpha);
1331b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        }
1332b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    }
1333b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek
13341685e634fb0b14033bd436af8d7174436699ffecSelim Cinek    public int getMaxExpandHeight() {
1335b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        return mMaxExpandHeight;
1336a5e0f415d351ad1a9c0ffde8d93df91a2384591fDan Sandler    }
1337584a7aa62c54bcbd654a6696d4fbb56e124874e7Jorim Jaggi
133834958fa272c9216db4002546c3efad692b3d7775Mady Mellor    public boolean areGutsExposed() {
133934958fa272c9216db4002546c3efad692b3d7775Mady Mellor        return (mGuts != null && mGuts.areGutsExposed());
134034958fa272c9216db4002546c3efad692b3d7775Mady Mellor    }
134134958fa272c9216db4002546c3efad692b3d7775Mady Mellor
1342be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi    @Override
13434222d9a7fb87d73e1443ec1a2de9782b05741af6Jorim Jaggi    public boolean isContentExpandable() {
13442f0df8ae038dbb873bf2e11e1e13c75cf95b0198Selim Cinek        NotificationContentView showingLayout = getShowingLayout();
13452f0df8ae038dbb873bf2e11e1e13c75cf95b0198Selim Cinek        return showingLayout.isContentExpandable();
13464222d9a7fb87d73e1443ec1a2de9782b05741af6Jorim Jaggi    }
13474222d9a7fb87d73e1443ec1a2de9782b05741af6Jorim Jaggi
13484222d9a7fb87d73e1443ec1a2de9782b05741af6Jorim Jaggi    @Override
1349560e64d3d95a17123048bebe2fb06ffe4567fb78Selim Cinek    protected View getContentView() {
1350a5703187a9dba418f742fab0874a8f683b0bbb0eSelim Cinek        if (mIsSummaryWithChildren) {
1351a5703187a9dba418f742fab0874a8f683b0bbb0eSelim Cinek            return mChildrenContainer;
1352a5703187a9dba418f742fab0874a8f683b0bbb0eSelim Cinek        }
1353560e64d3d95a17123048bebe2fb06ffe4567fb78Selim Cinek        return getShowingLayout();
1354560e64d3d95a17123048bebe2fb06ffe4567fb78Selim Cinek    }
1355560e64d3d95a17123048bebe2fb06ffe4567fb78Selim Cinek
1356560e64d3d95a17123048bebe2fb06ffe4567fb78Selim Cinek    @Override
1357d552d9d8e964c102e6832610be46cf2c041e8829Jorim Jaggi    public void setActualHeight(int height, boolean notifyListeners) {
1358b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        super.setActualHeight(height, notifyListeners);
1359b53bc276d6ec093817988a358b7c2a6c63ee0c48Mady Mellor        if (mGuts != null && mGuts.areGutsExposed()) {
1360b53bc276d6ec093817988a358b7c2a6c63ee0c48Mady Mellor            mGuts.setActualHeight(height);
1361b53bc276d6ec093817988a358b7c2a6c63ee0c48Mady Mellor            return;
1362b53bc276d6ec093817988a358b7c2a6c63ee0c48Mady Mellor        }
1363eef842851026a90b6a217d8bc423454fa48df4feSelim Cinek        int contentHeight = Math.max(getMinHeight(), height);
1364b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        mPrivateLayout.setContentHeight(contentHeight);
1365b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek        mPublicLayout.setContentHeight(contentHeight);
136642357e030c095867b95e2e8a718649587c5ebf52Selim Cinek        if (mIsSummaryWithChildren) {
136742357e030c095867b95e2e8a718649587c5ebf52Selim Cinek            mChildrenContainer.setActualHeight(height);
136842357e030c095867b95e2e8a718649587c5ebf52Selim Cinek        }
1369b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi        if (mGuts != null) {
1370b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi            mGuts.setActualHeight(height);
1371b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi        }
1372be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi    }
1373be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi
1374be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi    @Override
1375b5605e58cb8080c8c887b1885336b707596c8094Selim Cinek    public int getMaxContentHeight() {
137683bc78338437a460076a4b5778ded38440ac3501Selim Cinek        if (mIsSummaryWithChildren && !mShowingPublic) {
1377eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek            return mChildrenContainer.getMaxContentHeight();
137883bc78338437a460076a4b5778ded38440ac3501Selim Cinek        }
13792f0df8ae038dbb873bf2e11e1e13c75cf95b0198Selim Cinek        NotificationContentView showingLayout = getShowingLayout();
13802f0df8ae038dbb873bf2e11e1e13c75cf95b0198Selim Cinek        return showingLayout.getMaxHeight();
1381be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi    }
1382be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi
1383be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi    @Override
13844222d9a7fb87d73e1443ec1a2de9782b05741af6Jorim Jaggi    public int getMinHeight() {
138531aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        if (mIsHeadsUp && mHeadsUpManager.isTrackingHeadsUp()) {
138631aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek                return getPinnedHeadsUpHeight(false /* atLeastMinHeight */);
138731aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        } else if (mIsSummaryWithChildren && !isGroupExpanded() && !mShowingPublic) {
1388b55386d64aeb80f74ed21035d1e389d86be89db6Selim Cinek            return mChildrenContainer.getMinHeight();
138931aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        } else if (mIsHeadsUp) {
139031aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek            return mHeadsUpHeight;
1391b55386d64aeb80f74ed21035d1e389d86be89db6Selim Cinek        }
1392816c8e4735f975f4d8bffa1a5a37be6557424ea3Selim Cinek        NotificationContentView showingLayout = getShowingLayout();
1393816c8e4735f975f4d8bffa1a5a37be6557424ea3Selim Cinek        return showingLayout.getMinHeight();
1394816c8e4735f975f4d8bffa1a5a37be6557424ea3Selim Cinek    }
1395816c8e4735f975f4d8bffa1a5a37be6557424ea3Selim Cinek
1396816c8e4735f975f4d8bffa1a5a37be6557424ea3Selim Cinek    @Override
1397567e845d99840a6e556595739a15e16132eb2f1eSelim Cinek    public int getCollapsedHeight() {
13982c58461daf909fae5a2605f0ba63da3f9c897731Selim Cinek        if (mIsSummaryWithChildren && !mShowingPublic) {
1399567e845d99840a6e556595739a15e16132eb2f1eSelim Cinek            return mChildrenContainer.getCollapsedHeight();
140083bc78338437a460076a4b5778ded38440ac3501Selim Cinek        }
1401816c8e4735f975f4d8bffa1a5a37be6557424ea3Selim Cinek        return getMinHeight();
14024222d9a7fb87d73e1443ec1a2de9782b05741af6Jorim Jaggi    }
14034222d9a7fb87d73e1443ec1a2de9782b05741af6Jorim Jaggi
14044222d9a7fb87d73e1443ec1a2de9782b05741af6Jorim Jaggi    @Override
1405be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi    public void setClipTopAmount(int clipTopAmount) {
1406be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi        super.setClipTopAmount(clipTopAmount);
1407be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi        mPrivateLayout.setClipTopAmount(clipTopAmount);
14082f0df8ae038dbb873bf2e11e1e13c75cf95b0198Selim Cinek        mPublicLayout.setClipTopAmount(clipTopAmount);
1409b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi        if (mGuts != null) {
1410b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi            mGuts.setClipTopAmount(clipTopAmount);
1411b1cd3c1945499721d7d1ce57bdda67695ffe936bJorim Jaggi        }
1412be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi    }
1413be565dfc1c17b7ddafa9753851b8f82849fd3f42Jorim Jaggi
1414eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek    private void recreateNotificationHeader() {
1415eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        final Notification.Builder builder = Notification.Builder.recoverBuilder(getContext(),
1416eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek                getStatusBarNotification().getNotification());
1417eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        final RemoteViews header = builder.makeNotificationHeader();
1418eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        if (mNotificationHeader == null) {
1419eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek            mNotificationHeader = (NotificationHeaderView) header.apply(getContext(), this);
1420eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek            final View expandButton = mNotificationHeader.findViewById(
1421eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek                    com.android.internal.R.id.expand_button);
1422eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek            expandButton.setVisibility(VISIBLE);
1423eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek            mNotificationHeader.setOnClickListener(mExpandClickListener);
14249c7712d45ccec56a80873a83e56a83f810624b43Selim Cinek            mNotificationHeaderWrapper = NotificationViewWrapper.wrap(getContext(),
14257d1c63e66a2e19bf32249f52c56e563eae4c6819Selim Cinek                    mNotificationHeader, this);
1426b5a83613fe935cc60106746d311bab2acbce37faSelim Cinek            addView(mNotificationHeader, indexOfChild(mChildrenContainer) + 1);
14274b80b1025f82fa7becc8e126bfa4aea39affcf65Mady Mellor            mTranslateableViews.add(mNotificationHeader);
1428eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        } else {
1429eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek            header.reapply(getContext(), mNotificationHeader);
14304ffd63611a0d516c9988b37e9c06e6f8390c2a2fSelim Cinek            mNotificationHeaderWrapper.notifyContentUpdated(mEntry.notification);
1431eaa29ca6ff7a4c21a0729118d0e7c38750b9c93eSelim Cinek        }
1432ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek        updateChildrenHeaderAppearance();
1433343e6e258ab6a9f647eabebaed05ce3acafd2ff1Selim Cinek    }
14347d447726e2cb9fae80db417012039828daab8fe7Selim Cinek
1435ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek    public void updateChildrenHeaderAppearance() {
1436ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek        if (mIsSummaryWithChildren) {
1437ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek            mHeaderUtil.updateChildrenHeaderAppearance();
1438ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek        }
1439ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek    }
1440ea4bef7386ca6c6260f292bf006d16a99b93f698Selim Cinek
144131094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek    public boolean isMaxExpandHeightInitialized() {
144231094df5c6e3cb3a4a4faacb091e35eea1f6a5deSelim Cinek        return mMaxExpandHeight != 0;
14437d447726e2cb9fae80db417012039828daab8fe7Selim Cinek    }
14442f0df8ae038dbb873bf2e11e1e13c75cf95b0198Selim Cinek
144542357e030c095867b95e2e8a718649587c5ebf52Selim Cinek    public NotificationContentView getShowingLayout() {
14462f0df8ae038dbb873bf2e11e1e13c75cf95b0198Selim Cinek        return mShowingPublic ? mPublicLayout : mPrivateLayout;
14472f0df8ae038dbb873bf2e11e1e13c75cf95b0198Selim Cinek    }
144878403d79739605511ea88b653564d81d7bf4bbbaChris Wren
144959ec304eaebf1bc4098d6feb6cca9039c8b70d3dJorim Jaggi    @Override
145059ec304eaebf1bc4098d6feb6cca9039c8b70d3dJorim Jaggi    public void setShowingLegacyBackground(boolean showing) {
145159ec304eaebf1bc4098d6feb6cca9039c8b70d3dJorim Jaggi        super.setShowingLegacyBackground(showing);
145259ec304eaebf1bc4098d6feb6cca9039c8b70d3dJorim Jaggi        mPrivateLayout.setShowingLegacyBackground(showing);
145359ec304eaebf1bc4098d6feb6cca9039c8b70d3dJorim Jaggi        mPublicLayout.setShowingLegacyBackground(showing);
145459ec304eaebf1bc4098d6feb6cca9039c8b70d3dJorim Jaggi    }
145559ec304eaebf1bc4098d6feb6cca9039c8b70d3dJorim Jaggi
1456a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek    @Override
1457a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek    protected void updateBackgroundTint() {
1458a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek        super.updateBackgroundTint();
1459a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek        updateNoBackgroundState();
1460a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek        if (mIsSummaryWithChildren) {
1461a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek            List<ExpandableNotificationRow> notificationChildren =
1462a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek                    mChildrenContainer.getNotificationChildren();
1463a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek            for (int i = 0; i < notificationChildren.size(); i++) {
1464a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek                ExpandableNotificationRow child = notificationChildren.get(i);
1465a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek                child.updateNoBackgroundState();
1466a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek            }
1467a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek        }
1468a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek    }
1469a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek
1470a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek    private void updateNoBackgroundState() {
1471a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek        mShowNoBackground = isChildInGroup() && hasSameBgColor(mNotificationParent);
1472a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek        updateBackground();
1473a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek    }
1474a6c6bfb61ba14b0467b73082d591c834576cddf4Selim Cinek
147578403d79739605511ea88b653564d81d7bf4bbbaChris Wren    public void setExpansionLogger(ExpansionLogger logger, String key) {
147678403d79739605511ea88b653564d81d7bf4bbbaChris Wren        mLogger = logger;
147778403d79739605511ea88b653564d81d7bf4bbbaChris Wren        mLoggingKey = key;
147878403d79739605511ea88b653564d81d7bf4bbbaChris Wren    }
147978403d79739605511ea88b653564d81d7bf4bbbaChris Wren
14806183d12926a189b08cc3be8d9c78470617e63db0Selim Cinek    @Override
148142357e030c095867b95e2e8a718649587c5ebf52Selim Cinek    public float getIncreasedPaddingAmount() {
148242357e030c095867b95e2e8a718649587c5ebf52Selim Cinek        if (mIsSummaryWithChildren) {
148342357e030c095867b95e2e8a718649587c5ebf52Selim Cinek            if (isGroupExpanded()) {
148442357e030c095867b95e2e8a718649587c5ebf52Selim Cinek                return 1.0f;
148542357e030c095867b95e2e8a718649587c5ebf52Selim Cinek            } else if (isUserLocked()) {
1486f07d06212b08939809aa4128f153bd5179f81fc7Selim Cinek                return mChildrenContainer.getGroupExpandFraction();
148742357e030c095867b95e2e8a718649587c5ebf52Selim Cinek            }
148842357e030c095867b95e2e8a718649587c5ebf52Selim Cinek        }
148942357e030c095867b95e2e8a718649587c5ebf52Selim Cinek        return 0.0f;
149061633a8db8dfdefa84b4444a7ae668d0e24f53e9Selim Cinek    }
149161633a8db8dfdefa84b4444a7ae668d0e24f53e9Selim Cinek
149261633a8db8dfdefa84b4444a7ae668d0e24f53e9Selim Cinek    @Override
14936183d12926a189b08cc3be8d9c78470617e63db0Selim Cinek    protected boolean disallowSingleClick(MotionEvent event) {
14946183d12926a189b08cc3be8d9c78470617e63db0Selim Cinek        float x = event.getX();
14956183d12926a189b08cc3be8d9c78470617e63db0Selim Cinek        float y = event.getY();
149634eda5ed70863320e41b6860a550ba6a4248c652Selim Cinek        NotificationHeaderView header = getVisibleNotificationHeader();
14976183d12926a189b08cc3be8d9c78470617e63db0Selim Cinek        if (header != null) {
1498a883351024f8dbdf8041c551f8a8987d9357dcd8Mady Mellor            return header.isInTouchRect(x - getTranslation(), y);
14996183d12926a189b08cc3be8d9c78470617e63db0Selim Cinek        }
15006183d12926a189b08cc3be8d9c78470617e63db0Selim Cinek        return super.disallowSingleClick(event);
15016183d12926a189b08cc3be8d9c78470617e63db0Selim Cinek    }
15026183d12926a189b08cc3be8d9c78470617e63db0Selim Cinek
150378403d79739605511ea88b653564d81d7bf4bbbaChris Wren    private void logExpansionEvent(boolean userAction, boolean wasExpanded) {
150478403d79739605511ea88b653564d81d7bf4bbbaChris Wren        final boolean nowExpanded = isExpanded();
150578403d79739605511ea88b653564d81d7bf4bbbaChris Wren        if (wasExpanded != nowExpanded && mLogger != null) {
150678403d79739605511ea88b653564d81d7bf4bbbaChris Wren            mLogger.logNotificationExpansion(mLoggingKey, userAction, nowExpanded) ;
150778403d79739605511ea88b653564d81d7bf4bbbaChris Wren        }
150878403d79739605511ea88b653564d81d7bf4bbbaChris Wren    }
1509570981d5f1bcd0e5186cc02655254a0606b6ec14Selim Cinek
1510570981d5f1bcd0e5186cc02655254a0606b6ec14Selim Cinek    public interface OnExpandClickListener {
151131aada4ef4ff37f8cdc110b196c06918841647c7Selim Cinek        void onExpandClicked(NotificationData.Entry clickedEntry, boolean nowExpanded);
1512570981d5f1bcd0e5186cc02655254a0606b6ec14Selim Cinek    }
151351c7510e493680b4aca1ed7695b35c52d2cd63ffChris Wren}
1514