13a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn/* 23a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * Copyright (C) 2012 The Android Open Source Project 33a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * 43a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * Licensed under the Apache License, Version 2.0 (the "License"); 53a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * you may not use this file except in compliance with the License. 63a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * You may obtain a copy of the License at 73a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * 83a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * http://www.apache.org/licenses/LICENSE-2.0 93a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * 103a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * Unless required by applicable law or agreed to in writing, software 113a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * distributed under the License is distributed on an "AS IS" BASIS, 123a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 133a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * See the License for the specific language governing permissions and 143a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * limitations under the License. 153a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn */ 163a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 173a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackbornpackage com.android.internal.widget; 183a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 19b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powellimport android.animation.Animator; 20b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powellimport android.animation.AnimatorListenerAdapter; 213a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackbornimport android.content.Context; 224369e7d0b087d777e5012e2706acc5be9be47de7Adam Powellimport android.content.pm.ActivityInfo; 23720924b6a9770f03355999102a11d98c5954407cAdam Powellimport android.content.res.Configuration; 243a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackbornimport android.content.res.TypedArray; 25b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powellimport android.graphics.Canvas; 263a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackbornimport android.graphics.Rect; 27b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powellimport android.graphics.drawable.Drawable; 28b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powellimport android.os.Build; 294369e7d0b087d777e5012e2706acc5be9be47de7Adam Powellimport android.os.Parcelable; 303a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackbornimport android.util.AttributeSet; 31b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powellimport android.util.IntProperty; 324369e7d0b087d777e5012e2706acc5be9be47de7Adam Powellimport android.util.Log; 33b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powellimport android.util.Property; 344369e7d0b087d777e5012e2706acc5be9be47de7Adam Powellimport android.util.SparseArray; 354369e7d0b087d777e5012e2706acc5be9be47de7Adam Powellimport android.view.KeyEvent; 364369e7d0b087d777e5012e2706acc5be9be47de7Adam Powellimport android.view.Menu; 373a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackbornimport android.view.View; 38b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powellimport android.view.ViewGroup; 39b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powellimport android.view.ViewPropertyAnimator; 404369e7d0b087d777e5012e2706acc5be9be47de7Adam Powellimport android.view.Window; 41b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powellimport android.view.WindowInsets; 42b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powellimport android.widget.OverScroller; 43e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powellimport android.widget.Toolbar; 444369e7d0b087d777e5012e2706acc5be9be47de7Adam Powellimport com.android.internal.view.menu.MenuPresenter; 453a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 463a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn/** 473a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * Special layout for the containing of an overlay action bar (and its 483a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * content) to correctly handle fitting system windows when the content 493a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn * has request that its layout ignore them. 503a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn */ 514369e7d0b087d777e5012e2706acc5be9be47de7Adam Powellpublic class ActionBarOverlayLayout extends ViewGroup implements DecorContentParent { 529b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell private static final String TAG = "ActionBarOverlayLayout"; 539b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell 543a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn private int mActionBarHeight; 55b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell //private WindowDecorActionBar mActionBar; 563a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn private int mWindowVisibility = View.VISIBLE; 571dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 581dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // The main UI elements that we handle the layout of. 593a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn private View mContent; 604369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell private ActionBarContainer mActionBarBottom; 619b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell private ActionBarContainer mActionBarTop; 621dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 631dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // Some interior UI elements. 64e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell private DecorToolbar mDecorToolbar; 659b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell 669b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell // Content overlay drawable - generally the action bar's shadow 679b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell private Drawable mWindowContentOverlay; 689b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell private boolean mIgnoreWindowContentOverlay; 691dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 70df7221ced3b7cd807f14e84c302fc09fd659fd68Dianne Hackborn private boolean mOverlayMode; 71b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private boolean mHasNonEmbeddedTabs; 72b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private boolean mHideOnContentScroll; 73b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private boolean mAnimatingForFling; 74b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private int mHideOnContentScrollReference; 753a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn private int mLastSystemUiVisibility; 761dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn private final Rect mBaseContentInsets = new Rect(); 771dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn private final Rect mLastBaseContentInsets = new Rect(); 781dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn private final Rect mContentInsets = new Rect(); 791dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn private final Rect mBaseInnerInsets = new Rect(); 801dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn private final Rect mInnerInsets = new Rect(); 811dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn private final Rect mLastInnerInsets = new Rect(); 823a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 83b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private ActionBarVisibilityCallback mActionBarVisibilityCallback; 84b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 85b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private final int ACTION_BAR_ANIMATE_DELAY = 600; // ms 86b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 87b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private OverScroller mFlingEstimator; 88b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 89b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private ViewPropertyAnimator mCurrentActionBarTopAnimator; 90b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private ViewPropertyAnimator mCurrentActionBarBottomAnimator; 91b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 92b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private final Animator.AnimatorListener mTopAnimatorListener = new AnimatorListenerAdapter() { 93b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell @Override 94b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void onAnimationEnd(Animator animation) { 95b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mCurrentActionBarTopAnimator = null; 96b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mAnimatingForFling = false; 97b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 98b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 99b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell @Override 100b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void onAnimationCancel(Animator animation) { 101b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mCurrentActionBarTopAnimator = null; 102b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mAnimatingForFling = false; 103b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 104b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell }; 105b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 106b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private final Animator.AnimatorListener mBottomAnimatorListener = 107b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell new AnimatorListenerAdapter() { 108b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell @Override 109b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void onAnimationEnd(Animator animation) { 110b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mCurrentActionBarBottomAnimator = null; 111b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mAnimatingForFling = false; 112b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 113b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 114b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell @Override 115b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void onAnimationCancel(Animator animation) { 116b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mCurrentActionBarBottomAnimator = null; 117b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mAnimatingForFling = false; 118b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 119b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell }; 120b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 121b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private final Runnable mRemoveActionBarHideOffset = new Runnable() { 122b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void run() { 123b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell haltActionBarHideOffsetAnimations(); 124b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mCurrentActionBarTopAnimator = mActionBarTop.animate().translationY(0) 125b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell .setListener(mTopAnimatorListener); 126b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mActionBarBottom != null && mActionBarBottom.getVisibility() != GONE) { 127b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mCurrentActionBarBottomAnimator = mActionBarBottom.animate().translationY(0) 128b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell .setListener(mBottomAnimatorListener); 129b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 130b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 131b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell }; 132b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 133b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private final Runnable mAddActionBarHideOffset = new Runnable() { 134b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void run() { 135b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell haltActionBarHideOffsetAnimations(); 136b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mCurrentActionBarTopAnimator = mActionBarTop.animate() 137b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell .translationY(-mActionBarTop.getHeight()) 138b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell .setListener(mTopAnimatorListener); 139b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mActionBarBottom != null && mActionBarBottom.getVisibility() != GONE) { 140b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mCurrentActionBarBottomAnimator = mActionBarBottom.animate() 141b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell .translationY(mActionBarBottom.getHeight()) 142b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell .setListener(mBottomAnimatorListener); 143b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 144b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 145b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell }; 146b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 147b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public static final Property<ActionBarOverlayLayout, Integer> ACTION_BAR_HIDE_OFFSET = 148b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell new IntProperty<ActionBarOverlayLayout>("actionBarHideOffset") { 149b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 150b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell @Override 151b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void setValue(ActionBarOverlayLayout object, int value) { 152b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell object.setActionBarHideOffset(value); 153b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 154b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 155b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell @Override 156b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public Integer get(ActionBarOverlayLayout object) { 157b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell return object.getActionBarHideOffset(); 158b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 159b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell }; 160b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 1619b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell static final int[] ATTRS = new int [] { 1629b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell com.android.internal.R.attr.actionBarSize, 1639b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell com.android.internal.R.attr.windowContentOverlay 1643a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn }; 1653a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 1663a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn public ActionBarOverlayLayout(Context context) { 1673a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn super(context); 1683a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn init(context); 1693a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 1703a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 1713a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn public ActionBarOverlayLayout(Context context, AttributeSet attrs) { 1723a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn super(context, attrs); 1733a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn init(context); 1743a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 1753a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 1763a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn private void init(Context context) { 1779b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell TypedArray ta = getContext().getTheme().obtainStyledAttributes(ATTRS); 1783a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn mActionBarHeight = ta.getDimensionPixelSize(0, 0); 1799b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell mWindowContentOverlay = ta.getDrawable(1); 1809b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell setWillNotDraw(mWindowContentOverlay == null); 1813a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn ta.recycle(); 1829b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell 1839b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell mIgnoreWindowContentOverlay = context.getApplicationInfo().targetSdkVersion < 184e8222dddaf2e3da14380101e818d4254899e0c0dChet Haase Build.VERSION_CODES.KITKAT; 185b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 186b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mFlingEstimator = new OverScroller(context); 187b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 188b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 189b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell @Override 190b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell protected void onDetachedFromWindow() { 191b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell super.onDetachedFromWindow(); 192b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell haltActionBarHideOffsetAnimations(); 1933a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 1943a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 195b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void setActionBarVisibilityCallback(ActionBarVisibilityCallback cb) { 196b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mActionBarVisibilityCallback = cb; 1973a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn if (getWindowToken() != null) { 1983a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn // This is being initialized after being added to a window; 1993a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn // make sure to update all state now. 200b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mActionBarVisibilityCallback.onWindowVisibilityChanged(mWindowVisibility); 2013a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn if (mLastSystemUiVisibility != 0) { 2023a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn int newVis = mLastSystemUiVisibility; 2033a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn onWindowSystemUiVisibilityChanged(newVis); 20446e38fd9abe1af3ccb903a80ff89bc3faef4d3e3Adam Powell requestApplyInsets(); 2053a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 2063a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 2073a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 2083a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 2099b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell public void setOverlayMode(boolean overlayMode) { 2109b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell mOverlayMode = overlayMode; 2119b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell 2129b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell /* 2139b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell * Drawing the window content overlay was broken before K so starting to draw it 2149b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell * again unexpectedly will cause artifacts in some apps. They should fix it. 2159b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell */ 2169b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell mIgnoreWindowContentOverlay = overlayMode && 2179b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell getContext().getApplicationInfo().targetSdkVersion < 218e8222dddaf2e3da14380101e818d4254899e0c0dChet Haase Build.VERSION_CODES.KITKAT; 2199b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell } 2209b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell 221b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public boolean isInOverlayMode() { 222b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell return mOverlayMode; 223b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 224b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 225b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void setHasNonEmbeddedTabs(boolean hasNonEmbeddedTabs) { 226b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mHasNonEmbeddedTabs = hasNonEmbeddedTabs; 227b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 228b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 229139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn public void setShowingForActionMode(boolean showing) { 230139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn if (showing) { 231139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn // Here's a fun hack: if the status bar is currently being hidden, 232139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn // and the application has asked for stable content insets, then 233139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn // we will end up with the action mode action bar being shown 234139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn // without the status bar, but moved below where the status bar 235139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn // would be. Not nice. Trying to have this be positioned 236139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn // correctly is not easy (basically we need yet *another* content 237139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn // inset from the window manager to know where to put it), so 238139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn // instead we will just temporarily force the status bar to be shown. 239139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn if ((getWindowSystemUiVisibility() & (SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN 240139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn | SYSTEM_UI_FLAG_LAYOUT_STABLE)) 241139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn == (SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN | SYSTEM_UI_FLAG_LAYOUT_STABLE)) { 242139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn setDisabledSystemUiVisibility(SYSTEM_UI_FLAG_FULLSCREEN); 243139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn } 244139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn } else { 245139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn setDisabledSystemUiVisibility(0); 246139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn } 247139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn } 248139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn 2493a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn @Override 250720924b6a9770f03355999102a11d98c5954407cAdam Powell protected void onConfigurationChanged(Configuration newConfig) { 251720924b6a9770f03355999102a11d98c5954407cAdam Powell super.onConfigurationChanged(newConfig); 252720924b6a9770f03355999102a11d98c5954407cAdam Powell init(getContext()); 253720924b6a9770f03355999102a11d98c5954407cAdam Powell requestApplyInsets(); 254720924b6a9770f03355999102a11d98c5954407cAdam Powell } 255720924b6a9770f03355999102a11d98c5954407cAdam Powell 256720924b6a9770f03355999102a11d98c5954407cAdam Powell @Override 2573a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn public void onWindowSystemUiVisibilityChanged(int visible) { 2583a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn super.onWindowSystemUiVisibilityChanged(visible); 2593a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn pullChildren(); 2603a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn final int diff = mLastSystemUiVisibility ^ visible; 2613a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn mLastSystemUiVisibility = visible; 262b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell final boolean barVisible = (visible & SYSTEM_UI_FLAG_FULLSCREEN) == 0; 263b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell final boolean stable = (visible & SYSTEM_UI_FLAG_LAYOUT_STABLE) != 0; 264b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mActionBarVisibilityCallback != null) { 265df7221ced3b7cd807f14e84c302fc09fd659fd68Dianne Hackborn // We want the bar to be visible if it is not being hidden, 266df7221ced3b7cd807f14e84c302fc09fd659fd68Dianne Hackborn // or the app has not turned on a stable UI mode (meaning they 267df7221ced3b7cd807f14e84c302fc09fd659fd68Dianne Hackborn // are performing explicit layout around the action bar). 268b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mActionBarVisibilityCallback.enableContentAnimations(!stable); 269b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (barVisible || !stable) mActionBarVisibilityCallback.showForSystem(); 270b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell else mActionBarVisibilityCallback.hideForSystem(); 271139e5aa1da51b27231ab36344cf2d0dafab23f1eDianne Hackborn } 272b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if ((diff & SYSTEM_UI_FLAG_LAYOUT_STABLE) != 0) { 273b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mActionBarVisibilityCallback != null) { 27446e38fd9abe1af3ccb903a80ff89bc3faef4d3e3Adam Powell requestApplyInsets(); 2753a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 2763a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 2773a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 2783a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 2793a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn @Override 2803a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn protected void onWindowVisibilityChanged(int visibility) { 2813a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn super.onWindowVisibilityChanged(visibility); 2823a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn mWindowVisibility = visibility; 283b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mActionBarVisibilityCallback != null) { 284b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mActionBarVisibilityCallback.onWindowVisibilityChanged(visibility); 2853a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 2863a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 2873a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 2883a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn private boolean applyInsets(View view, Rect insets, boolean left, boolean top, 2893a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn boolean bottom, boolean right) { 2903a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn boolean changed = false; 2911dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn LayoutParams lp = (LayoutParams)view.getLayoutParams(); 2923a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn if (left && lp.leftMargin != insets.left) { 2933a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn changed = true; 2943a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn lp.leftMargin = insets.left; 2953a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 2963a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn if (top && lp.topMargin != insets.top) { 2973a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn changed = true; 2983a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn lp.topMargin = insets.top; 2993a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 3003a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn if (right && lp.rightMargin != insets.right) { 3013a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn changed = true; 3023a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn lp.rightMargin = insets.right; 3033a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 3043a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn if (bottom && lp.bottomMargin != insets.bottom) { 3053a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn changed = true; 3063a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn lp.bottomMargin = insets.bottom; 3073a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 3083a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn return changed; 3093a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 3103a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 3113a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn @Override 31246e38fd9abe1af3ccb903a80ff89bc3faef4d3e3Adam Powell public WindowInsets onApplyWindowInsets(WindowInsets insets) { 3133a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn pullChildren(); 3143a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 3153a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn final int vis = getWindowSystemUiVisibility(); 3163a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn final boolean stable = (vis & SYSTEM_UI_FLAG_LAYOUT_STABLE) != 0; 31746e38fd9abe1af3ccb903a80ff89bc3faef4d3e3Adam Powell final Rect systemInsets = insets.getSystemWindowInsets(); 3183a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 3193a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn // The top and bottom action bars are always within the content area. 32046e38fd9abe1af3ccb903a80ff89bc3faef4d3e3Adam Powell boolean changed = applyInsets(mActionBarTop, systemInsets, true, true, false, true); 321474690caf8b3bece133b40914979ac2520036989Dianne Hackborn if (mActionBarBottom != null) { 32246e38fd9abe1af3ccb903a80ff89bc3faef4d3e3Adam Powell changed |= applyInsets(mActionBarBottom, systemInsets, true, false, true, true); 323474690caf8b3bece133b40914979ac2520036989Dianne Hackborn } 3241dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 32546e38fd9abe1af3ccb903a80ff89bc3faef4d3e3Adam Powell mBaseInnerInsets.set(systemInsets); 3261dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn computeFitSystemWindows(mBaseInnerInsets, mBaseContentInsets); 3271dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn if (!mLastBaseContentInsets.equals(mBaseContentInsets)) { 3281dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn changed = true; 3291dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn mLastBaseContentInsets.set(mBaseContentInsets); 330fe2b7ccca4c5fdaa0d77968b897bd789f4c87c30Dianne Hackborn } 3313a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 3321dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn if (changed) { 3331dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn requestLayout(); 3343a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 3351dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 3361dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // We don't do any more at this point. To correctly compute the content/inner 3371dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // insets in all cases, we need to know the measured size of the various action 33846e38fd9abe1af3ccb903a80ff89bc3faef4d3e3Adam Powell // bar elements. onApplyWindowInsets() happens before the measure pass, so we can't 3391dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // do that here. Instead we will take this up in onMeasure(). 340720924b6a9770f03355999102a11d98c5954407cAdam Powell return WindowInsets.CONSUMED; 3411dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 3421dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 3431dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn @Override 3441dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn protected LayoutParams generateDefaultLayoutParams() { 3451dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn return new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT); 3461dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 3471dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 3481dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn @Override 3491dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn public LayoutParams generateLayoutParams(AttributeSet attrs) { 3501dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn return new LayoutParams(getContext(), attrs); 3511dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 3521dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 3531dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn @Override 3547cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn protected ViewGroup.LayoutParams generateLayoutParams(ViewGroup.LayoutParams p) { 3557cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn return new LayoutParams(p); 3567cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn } 3577cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn 3587cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn @Override 3597cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn protected boolean checkLayoutParams(ViewGroup.LayoutParams p) { 3607cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn return p instanceof LayoutParams; 3617cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn } 3627cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn 3637cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn @Override 3641dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { 365474690caf8b3bece133b40914979ac2520036989Dianne Hackborn pullChildren(); 366474690caf8b3bece133b40914979ac2520036989Dianne Hackborn 3671dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn int maxHeight = 0; 3681dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn int maxWidth = 0; 3691dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn int childState = 0; 3701dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 3711dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn int topInset = 0; 3721dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn int bottomInset = 0; 3731dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 3741dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn measureChildWithMargins(mActionBarTop, widthMeasureSpec, 0, heightMeasureSpec, 0); 3751dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn LayoutParams lp = (LayoutParams) mActionBarTop.getLayoutParams(); 3761dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn maxWidth = Math.max(maxWidth, 3771dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn mActionBarTop.getMeasuredWidth() + lp.leftMargin + lp.rightMargin); 3781dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn maxHeight = Math.max(maxHeight, 3791dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn mActionBarTop.getMeasuredHeight() + lp.topMargin + lp.bottomMargin); 3801dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn childState = combineMeasuredStates(childState, mActionBarTop.getMeasuredState()); 3811dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 382474690caf8b3bece133b40914979ac2520036989Dianne Hackborn // xlarge screen layout doesn't have bottom action bar. 383474690caf8b3bece133b40914979ac2520036989Dianne Hackborn if (mActionBarBottom != null) { 384474690caf8b3bece133b40914979ac2520036989Dianne Hackborn measureChildWithMargins(mActionBarBottom, widthMeasureSpec, 0, heightMeasureSpec, 0); 385474690caf8b3bece133b40914979ac2520036989Dianne Hackborn lp = (LayoutParams) mActionBarBottom.getLayoutParams(); 386474690caf8b3bece133b40914979ac2520036989Dianne Hackborn maxWidth = Math.max(maxWidth, 387474690caf8b3bece133b40914979ac2520036989Dianne Hackborn mActionBarBottom.getMeasuredWidth() + lp.leftMargin + lp.rightMargin); 388474690caf8b3bece133b40914979ac2520036989Dianne Hackborn maxHeight = Math.max(maxHeight, 389474690caf8b3bece133b40914979ac2520036989Dianne Hackborn mActionBarBottom.getMeasuredHeight() + lp.topMargin + lp.bottomMargin); 390474690caf8b3bece133b40914979ac2520036989Dianne Hackborn childState = combineMeasuredStates(childState, mActionBarBottom.getMeasuredState()); 391474690caf8b3bece133b40914979ac2520036989Dianne Hackborn } 3921dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 3931dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn final int vis = getWindowSystemUiVisibility(); 3941dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn final boolean stable = (vis & SYSTEM_UI_FLAG_LAYOUT_STABLE) != 0; 3951dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 3961dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn if (stable) { 3971dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // This is the standard space needed for the action bar. For stable measurement, 3981dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // we can't depend on the size currently reported by it -- this must remain constant. 3991dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn topInset = mActionBarHeight; 400b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mHasNonEmbeddedTabs) { 401b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell final View tabs = mActionBarTop.getTabContainer(); 4021dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn if (tabs != null) { 4031dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // If tabs are not embedded, increase space on top to account for them. 4041dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn topInset += mActionBarHeight; 4051dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 4063a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 40714a9738330c14410378fe2ba1c25404a444adaf3George Mount } else if (mActionBarTop.getVisibility() != GONE) { 4081dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // This is the space needed on top of the window for all of the action bar 4091dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // and tabs. 4101dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn topInset = mActionBarTop.getMeasuredHeight(); 4113a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 4123a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 413e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell if (mDecorToolbar.isSplit()) { 4141dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // If action bar is split, adjust bottom insets for it. 415474690caf8b3bece133b40914979ac2520036989Dianne Hackborn if (mActionBarBottom != null) { 416474690caf8b3bece133b40914979ac2520036989Dianne Hackborn if (stable) { 417474690caf8b3bece133b40914979ac2520036989Dianne Hackborn bottomInset = mActionBarHeight; 418474690caf8b3bece133b40914979ac2520036989Dianne Hackborn } else { 419474690caf8b3bece133b40914979ac2520036989Dianne Hackborn bottomInset = mActionBarBottom.getMeasuredHeight(); 420474690caf8b3bece133b40914979ac2520036989Dianne Hackborn } 4213a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 4223a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 4233a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 424df7221ced3b7cd807f14e84c302fc09fd659fd68Dianne Hackborn // If the window has not requested system UI layout flags, we need to 425df7221ced3b7cd807f14e84c302fc09fd659fd68Dianne Hackborn // make sure its content is not being covered by system UI... though it 4261dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // will still be covered by the action bar if they have requested it to 427df7221ced3b7cd807f14e84c302fc09fd659fd68Dianne Hackborn // overlay. 4281dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn mContentInsets.set(mBaseContentInsets); 4291dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn mInnerInsets.set(mBaseInnerInsets); 430df7221ced3b7cd807f14e84c302fc09fd659fd68Dianne Hackborn if (!mOverlayMode && !stable) { 4311dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn mContentInsets.top += topInset; 4321dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn mContentInsets.bottom += bottomInset; 433df7221ced3b7cd807f14e84c302fc09fd659fd68Dianne Hackborn } else { 4341dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn mInnerInsets.top += topInset; 4351dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn mInnerInsets.bottom += bottomInset; 436df7221ced3b7cd807f14e84c302fc09fd659fd68Dianne Hackborn } 4371dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn applyInsets(mContent, mContentInsets, true, true, true, true); 438df7221ced3b7cd807f14e84c302fc09fd659fd68Dianne Hackborn 4391dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn if (!mLastInnerInsets.equals(mInnerInsets)) { 4401dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // If the inner insets have changed, we need to dispatch this down to 4411dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // the app's fitSystemWindows(). We do this before measuring the content 4421dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // view to keep the same semantics as the normal fitSystemWindows() call. 4431dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn mLastInnerInsets.set(mInnerInsets); 44446e38fd9abe1af3ccb903a80ff89bc3faef4d3e3Adam Powell mContent.dispatchApplyWindowInsets(new WindowInsets(mInnerInsets)); 4453a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 4463a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 4471dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn measureChildWithMargins(mContent, widthMeasureSpec, 0, heightMeasureSpec, 0); 4481dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn lp = (LayoutParams) mContent.getLayoutParams(); 4491dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn maxWidth = Math.max(maxWidth, 4501dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn mContent.getMeasuredWidth() + lp.leftMargin + lp.rightMargin); 4511dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn maxHeight = Math.max(maxHeight, 4521dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn mContent.getMeasuredHeight() + lp.topMargin + lp.bottomMargin); 4531dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn childState = combineMeasuredStates(childState, mContent.getMeasuredState()); 4541dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 4551dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // Account for padding too 4561dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn maxWidth += getPaddingLeft() + getPaddingRight(); 4571dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn maxHeight += getPaddingTop() + getPaddingBottom(); 4581dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 4591dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn // Check against our minimum height and width 4601dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn maxHeight = Math.max(maxHeight, getSuggestedMinimumHeight()); 4611dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn maxWidth = Math.max(maxWidth, getSuggestedMinimumWidth()); 4621dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 4631dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn setMeasuredDimension(resolveSizeAndState(maxWidth, widthMeasureSpec, childState), 4641dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn resolveSizeAndState(maxHeight, heightMeasureSpec, 4651dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn childState << MEASURED_HEIGHT_STATE_SHIFT)); 4661dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 4671dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 4681dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn @Override 4691dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn protected void onLayout(boolean changed, int left, int top, int right, int bottom) { 4701dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn final int count = getChildCount(); 4711dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 4721dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn final int parentLeft = getPaddingLeft(); 4731dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn final int parentRight = right - left - getPaddingRight(); 4741dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 4751dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn final int parentTop = getPaddingTop(); 4761dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn final int parentBottom = bottom - top - getPaddingBottom(); 4771dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 4781dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn for (int i = 0; i < count; i++) { 4791dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn final View child = getChildAt(i); 4801dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn if (child.getVisibility() != GONE) { 4811dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn final LayoutParams lp = (LayoutParams) child.getLayoutParams(); 4821dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 4831dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn final int width = child.getMeasuredWidth(); 4841dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn final int height = child.getMeasuredHeight(); 4851dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 4861dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn int childLeft = parentLeft + lp.leftMargin; 4871dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn int childTop; 4881dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn if (child == mActionBarBottom) { 4891dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn childTop = parentBottom - height - lp.bottomMargin; 4901dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } else { 4911dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn childTop = parentTop + lp.topMargin; 4921dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 4931dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 4941dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn child.layout(childLeft, childTop, childLeft + width, childTop + height); 4951dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 4961dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 4973a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 4983a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn 4997cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn @Override 5009b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell public void draw(Canvas c) { 5019b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell super.draw(c); 5029b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell if (mWindowContentOverlay != null && !mIgnoreWindowContentOverlay) { 5039b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell final int top = mActionBarTop.getVisibility() == VISIBLE ? 5049b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell (int) (mActionBarTop.getBottom() + mActionBarTop.getTranslationY() + 0.5f) : 0; 5059b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell mWindowContentOverlay.setBounds(0, top, getWidth(), 5069b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell top + mWindowContentOverlay.getIntrinsicHeight()); 5079b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell mWindowContentOverlay.draw(c); 5089b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell } 5099b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell } 5109b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell 5119b0dc2894df1c3d26aa6196ecdef1989967e6ec9Adam Powell @Override 5127cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn public boolean shouldDelayChildPressedState() { 5137cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn return false; 5147cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn } 5157cf71fbdc3225778d0397b22cdaf40c812c15afbDianne Hackborn 516b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell @Override 517b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public boolean onStartNestedScroll(View child, View target, int axes) { 518b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if ((axes & SCROLL_AXIS_VERTICAL) == 0 || mActionBarTop.getVisibility() != VISIBLE) { 519b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell return false; 520b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 521b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell return mHideOnContentScroll; 522b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 523b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 524b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell @Override 525b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void onNestedScrollAccepted(View child, View target, int axes) { 526b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell super.onNestedScrollAccepted(child, target, axes); 527b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mHideOnContentScrollReference = getActionBarHideOffset(); 528b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell haltActionBarHideOffsetAnimations(); 529b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mActionBarVisibilityCallback != null) { 530b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mActionBarVisibilityCallback.onContentScrollStarted(); 531b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 532b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 533b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 534b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell @Override 535b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void onNestedScroll(View target, int dxConsumed, int dyConsumed, 536b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell int dxUnconsumed, int dyUnconsumed) { 537b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mHideOnContentScrollReference += dyConsumed; 538b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell setActionBarHideOffset(mHideOnContentScrollReference); 539b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 540b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 541b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell @Override 542b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void onStopNestedScroll(View target) { 543b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell super.onStopNestedScroll(target); 544b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mHideOnContentScroll && !mAnimatingForFling) { 545b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mHideOnContentScrollReference <= mActionBarTop.getHeight()) { 546b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell postRemoveActionBarHideOffset(); 547b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } else { 548b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell postAddActionBarHideOffset(); 549b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 550b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 551b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mActionBarVisibilityCallback != null) { 552b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mActionBarVisibilityCallback.onContentScrollStopped(); 553b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 554b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 555b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 556b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell @Override 557b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public boolean onNestedFling(View target, float velocityX, float velocityY, boolean consumed) { 558b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (!mHideOnContentScroll || !consumed) { 559b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell return false; 560b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 561b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (shouldHideActionBarOnFling(velocityX, velocityY)) { 562b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell addActionBarHideOffset(); 563b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } else { 564b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell removeActionBarHideOffset(); 565b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 566b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mAnimatingForFling = true; 567b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell return true; 568b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 569b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 5703a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn void pullChildren() { 5713a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn if (mContent == null) { 5723a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn mContent = findViewById(com.android.internal.R.id.content); 573b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mActionBarTop = (ActionBarContainer) findViewById( 5743a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn com.android.internal.R.id.action_bar_container); 575e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar = getDecorToolbar(findViewById(com.android.internal.R.id.action_bar)); 5764369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell mActionBarBottom = (ActionBarContainer) findViewById( 5774369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell com.android.internal.R.id.split_action_bar); 5783a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 5793a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn } 5801dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 581e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell private DecorToolbar getDecorToolbar(View view) { 582e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell if (view instanceof DecorToolbar) { 583e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell return (DecorToolbar) view; 584e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell } else if (view instanceof Toolbar) { 585e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell return ((Toolbar) view).getWrapper(); 586e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell } else { 587e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell throw new IllegalStateException("Can't make a decor toolbar out of " + 588e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell view.getClass().getSimpleName()); 589e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell } 590e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell } 591e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell 592b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void setHideOnContentScrollEnabled(boolean hideOnContentScroll) { 593b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (hideOnContentScroll != mHideOnContentScroll) { 594b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mHideOnContentScroll = hideOnContentScroll; 595b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (!hideOnContentScroll) { 596b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell stopNestedScroll(); 597b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell haltActionBarHideOffsetAnimations(); 598b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell setActionBarHideOffset(0); 599b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 600b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 601b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 602b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 603b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public boolean isHideOnContentScrollEnabled() { 604b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell return mHideOnContentScroll; 605b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 606b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 607b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public int getActionBarHideOffset() { 608c4b416f18d83100a386ab81e934e572cd471c4b3Adam Powell return mActionBarTop != null ? -((int) mActionBarTop.getTranslationY()) : 0; 609b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 610b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 611b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public void setActionBarHideOffset(int offset) { 612b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell haltActionBarHideOffsetAnimations(); 613b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell final int topHeight = mActionBarTop.getHeight(); 614b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell offset = Math.max(0, Math.min(offset, topHeight)); 615b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mActionBarTop.setTranslationY(-offset); 616b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mActionBarBottom != null && mActionBarBottom.getVisibility() != GONE) { 617b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell // Match the hide offset proportionally for a split bar 618b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell final float fOffset = (float) offset / topHeight; 619b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell final int bOffset = (int) (mActionBarBottom.getHeight() * fOffset); 620b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mActionBarBottom.setTranslationY(bOffset); 621b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 622b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 623b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 624b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private void haltActionBarHideOffsetAnimations() { 625b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell removeCallbacks(mRemoveActionBarHideOffset); 626b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell removeCallbacks(mAddActionBarHideOffset); 627b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mCurrentActionBarTopAnimator != null) { 628b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mCurrentActionBarTopAnimator.cancel(); 629b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 630b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell if (mCurrentActionBarBottomAnimator != null) { 631b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mCurrentActionBarBottomAnimator.cancel(); 632b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 633b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 634b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 635b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private void postRemoveActionBarHideOffset() { 636b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell haltActionBarHideOffsetAnimations(); 637b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell postDelayed(mRemoveActionBarHideOffset, ACTION_BAR_ANIMATE_DELAY); 638b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 639b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 640b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private void postAddActionBarHideOffset() { 641b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell haltActionBarHideOffsetAnimations(); 642b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell postDelayed(mAddActionBarHideOffset, ACTION_BAR_ANIMATE_DELAY); 643b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 644b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 645b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private void removeActionBarHideOffset() { 646b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell haltActionBarHideOffsetAnimations(); 647b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mRemoveActionBarHideOffset.run(); 648b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 649b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 650b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private void addActionBarHideOffset() { 651b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell haltActionBarHideOffsetAnimations(); 652b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mAddActionBarHideOffset.run(); 653b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 654b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 655b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell private boolean shouldHideActionBarOnFling(float velocityX, float velocityY) { 656b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell mFlingEstimator.fling(0, 0, 0, (int) velocityY, 0, 0, Integer.MIN_VALUE, Integer.MAX_VALUE); 657b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell final int finalY = mFlingEstimator.getFinalY(); 658b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell return finalY > mActionBarTop.getHeight(); 659b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 6601dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 6614369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 6624369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public void setWindowCallback(Window.Callback cb) { 6634369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 664e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.setWindowCallback(cb); 6654369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 6664369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 6674369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 6684369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public void setWindowTitle(CharSequence title) { 6694369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 670e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.setWindowTitle(title); 6714369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 6724369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 6734369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 6744369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public CharSequence getTitle() { 6754369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 676e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell return mDecorToolbar.getTitle(); 6774369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 6784369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 6794369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 6804369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public void initFeature(int windowFeature) { 6814369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 6824369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell switch (windowFeature) { 6834369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell case Window.FEATURE_PROGRESS: 684e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.initProgress(); 6854369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell break; 6864369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell case Window.FEATURE_INDETERMINATE_PROGRESS: 687e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.initIndeterminateProgress(); 6884369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell break; 6894369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell case Window.FEATURE_ACTION_BAR_OVERLAY: 6904369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell setOverlayMode(true); 6914369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell break; 6924369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 6934369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 6944369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 6954369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 6964369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public void setUiOptions(int uiOptions) { 6974369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell boolean splitActionBar = false; 6984369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell final boolean splitWhenNarrow = 6994369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell (uiOptions & ActivityInfo.UIOPTION_SPLIT_ACTION_BAR_WHEN_NARROW) != 0; 7004369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell if (splitWhenNarrow) { 7014369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell splitActionBar = getContext().getResources().getBoolean( 7024369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell com.android.internal.R.bool.split_action_bar_is_narrow); 7034369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7044369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell if (splitActionBar) { 7054369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 706e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell if (mActionBarBottom != null && mDecorToolbar.canSplit()) { 707e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.setSplitView(mActionBarBottom); 708e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.setSplitToolbar(splitActionBar); 709e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.setSplitWhenNarrow(splitWhenNarrow); 7104369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7114369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell final ActionBarContextView cab = (ActionBarContextView) findViewById( 7124369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell com.android.internal.R.id.action_context_bar); 7134369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell cab.setSplitView(mActionBarBottom); 714e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell cab.setSplitToolbar(splitActionBar); 7154369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell cab.setSplitWhenNarrow(splitWhenNarrow); 7164369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } else if (splitActionBar) { 7174369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell Log.e(TAG, "Requested split action bar with " + 7184369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell "incompatible window decor! Ignoring request."); 7194369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7204369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7214369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7224369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7234369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7244369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public boolean hasIcon() { 7254369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 726e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell return mDecorToolbar.hasIcon(); 7274369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7284369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7294369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7304369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public boolean hasLogo() { 7314369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 732e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell return mDecorToolbar.hasLogo(); 7334369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7344369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7354369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7364369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public void setIcon(int resId) { 7374369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 738e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.setIcon(resId); 7394369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7404369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7414369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7424369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public void setIcon(Drawable d) { 7434369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 744e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.setIcon(d); 7454369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7464369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7474369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7484369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public void setLogo(int resId) { 7494369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 750e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.setLogo(resId); 7514369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7524369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7534369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7544369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public boolean canShowOverflowMenu() { 7554369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 756e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell return mDecorToolbar.canShowOverflowMenu(); 7574369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7584369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7594369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7604369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public boolean isOverflowMenuShowing() { 7614369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 762e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell return mDecorToolbar.isOverflowMenuShowing(); 7634369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7644369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7654369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7664369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public boolean isOverflowMenuShowPending() { 7674369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 768e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell return mDecorToolbar.isOverflowMenuShowPending(); 7694369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7704369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7714369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7724369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public boolean showOverflowMenu() { 7734369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 774e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell return mDecorToolbar.showOverflowMenu(); 7754369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7764369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7774369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7784369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public boolean hideOverflowMenu() { 7794369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 780e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell return mDecorToolbar.hideOverflowMenu(); 7814369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7824369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7834369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7844369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public void setMenuPrepared() { 7854369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 786e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.setMenuPrepared(); 7874369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7884369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7894369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7904369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public void setMenu(Menu menu, MenuPresenter.Callback cb) { 7914369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 792e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.setMenu(menu, cb); 7934369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 7944369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 7954369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 7964369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public void saveToolbarHierarchyState(SparseArray<Parcelable> toolbarStates) { 7974369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 798e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.saveHierarchyState(toolbarStates); 7994369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 8004369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 8014369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 8024369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public void restoreToolbarHierarchyState(SparseArray<Parcelable> toolbarStates) { 8034369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 804e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.restoreHierarchyState(toolbarStates); 8054369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 8064369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 8074369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell @Override 8084369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell public void dismissPopups() { 8094369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell pullChildren(); 810e021e6ed8931a0a8296af182fc9b0c76b64fb0c4Adam Powell mDecorToolbar.dismissPopupMenus(); 8114369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell } 8124369e7d0b087d777e5012e2706acc5be9be47de7Adam Powell 8131dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn public static class LayoutParams extends MarginLayoutParams { 8141dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn public LayoutParams(Context c, AttributeSet attrs) { 8151dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn super(c, attrs); 8161dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 8171dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 8181dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn public LayoutParams(int width, int height) { 8191dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn super(width, height); 8201dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 8211dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 8221dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn public LayoutParams(ViewGroup.LayoutParams source) { 8231dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn super(source); 8241dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 8251dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn 8261dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn public LayoutParams(ViewGroup.MarginLayoutParams source) { 8271dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn super(source); 8281dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 8291dc5f92716189da02aa62f508adb6099061668b5Dianne Hackborn } 830b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell 831b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell public interface ActionBarVisibilityCallback { 832b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell void onWindowVisibilityChanged(int visibility); 833b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell void showForSystem(); 834b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell void hideForSystem(); 835b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell void enableContentAnimations(boolean enable); 836b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell void onContentScrollStarted(); 837b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell void onContentScrollStopped(); 838b36e4f944fe28ce68182f9ec91e5341866b49084Adam Powell } 8393a3a6cfd8ec12208ca75c0d0d871d19d76c34194Dianne Hackborn} 840