17edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock/* 27edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * Copyright (C) 2013 The Android Open Source Project 37edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * 47edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * Licensed under the Apache License, Version 2.0 (the "License"); 57edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * you may not use this file except in compliance with the License. 67edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * You may obtain a copy of the License at 77edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * 87edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * http://www.apache.org/licenses/LICENSE-2.0 97edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * 107edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * Unless required by applicable law or agreed to in writing, software 117edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * distributed under the License is distributed on an "AS IS" BASIS, 127edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 137edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * See the License for the specific language governing permissions and 147edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock * limitations under the License. 157edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock */ 167edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 177edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlockpackage com.android.systemui.statusbar.phone; 187edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 197edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlockimport android.content.Context; 202044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monkimport android.os.Handler; 212044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monkimport android.os.RemoteException; 227edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlockimport android.os.ServiceManager; 2340db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggiimport android.util.SparseArray; 242044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monkimport android.view.Display; 252044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monkimport android.view.IWallpaperVisibilityListener; 262044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monkimport android.view.IWindowManager; 277edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlockimport android.view.MotionEvent; 287edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlockimport android.view.View; 290e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monkimport android.view.View.OnLayoutChangeListener; 307edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 317edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlockimport com.android.internal.statusbar.IStatusBarService; 322044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monkimport com.android.systemui.Dependency; 337edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlockimport com.android.systemui.R; 347edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 357edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlockpublic final class NavigationBarTransitions extends BarTransitions { 367edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 377edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock private final NavigationBarView mView; 387edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock private final IStatusBarService mBarService; 3940db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi private final LightBarTransitionsController mLightTransitionsController; 403107d99e54795a4fadc5448014ffe2a1f8de7ce3Matthew Ng private final boolean mAllowAutoDimWallpaperNotVisible; 412044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk private boolean mWallpaperVisible; 427edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 437edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock private boolean mLightsOut; 44c2beef51306e8916f481218c449b9759ce017c09Jason Monk private boolean mAutoDim; 450e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk private View mNavButtons; 467edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 477edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock public NavigationBarTransitions(NavigationBarView view) { 487057d2c3a9a88f1d221bc69780385bd20c5b4999John Spurlock super(view, R.drawable.nav_background); 497edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock mView = view; 507edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock mBarService = IStatusBarService.Stub.asInterface( 517edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock ServiceManager.getService(Context.STATUS_BAR_SERVICE)); 52aa573e9e8632552d1fa8bdd6b0ee408ff9a93a6bJason Monk mLightTransitionsController = new LightBarTransitionsController(view.getContext(), 53aa573e9e8632552d1fa8bdd6b0ee408ff9a93a6bJason Monk this::applyDarkIntensity); 543107d99e54795a4fadc5448014ffe2a1f8de7ce3Matthew Ng mAllowAutoDimWallpaperNotVisible = view.getContext().getResources() 553107d99e54795a4fadc5448014ffe2a1f8de7ce3Matthew Ng .getBoolean(R.bool.config_navigation_bar_enable_auto_dim_no_visible_wallpaper); 562044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk 572044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk IWindowManager windowManagerService = Dependency.get(IWindowManager.class); 582044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk Handler handler = Handler.getMain(); 592044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk try { 602044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk mWallpaperVisible = windowManagerService.registerWallpaperVisibilityListener( 612044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk new IWallpaperVisibilityListener.Stub() { 622044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk @Override 632044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk public void onWallpaperVisibilityChanged(boolean newVisibility, 642044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk int displayId) throws RemoteException { 652044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk mWallpaperVisible = newVisibility; 662044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk handler.post(() -> applyLightsOut(true, false)); 672044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk } 682044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk }, Display.DEFAULT_DISPLAY); 692044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk } catch (RemoteException e) { 702044e6e3770ac3dd70b07ade58a7b8db19905a0fJason Monk } 710e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk mView.addOnLayoutChangeListener( 720e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk (v, left, top, right, bottom, oldLeft, oldTop, oldRight, oldBottom) -> { 730e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk View currentView = mView.getCurrentView(); 740e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk if (currentView != null) { 750e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk mNavButtons = currentView.findViewById(R.id.nav_buttons); 760e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk applyLightsOut(false, true); 770e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk } 780e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk }); 790e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk View currentView = mView.getCurrentView(); 800e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk if (currentView != null) { 810e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk mNavButtons = currentView.findViewById(R.id.nav_buttons); 820e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk } 837edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock } 847edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 858a8ffd4e9b15a04d2af0909205658f08c76bd6b2Adrian Roos public void init() { 86e631b41d8be2952db48df5838c6fb5d8df4645d1John Spurlock applyModeBackground(-1, getMode(), false /*animate*/); 87c2beef51306e8916f481218c449b9759ce017c09Jason Monk applyLightsOut(false /*animate*/, true /*force*/); 88c2beef51306e8916f481218c449b9759ce017c09Jason Monk } 89c2beef51306e8916f481218c449b9759ce017c09Jason Monk 90c2beef51306e8916f481218c449b9759ce017c09Jason Monk @Override 91c2beef51306e8916f481218c449b9759ce017c09Jason Monk public void setAutoDim(boolean autoDim) { 92c2beef51306e8916f481218c449b9759ce017c09Jason Monk if (mAutoDim == autoDim) return; 93c2beef51306e8916f481218c449b9759ce017c09Jason Monk mAutoDim = autoDim; 94c2beef51306e8916f481218c449b9759ce017c09Jason Monk applyLightsOut(true, false); 95c2beef51306e8916f481218c449b9759ce017c09Jason Monk } 96c2beef51306e8916f481218c449b9759ce017c09Jason Monk 97c2beef51306e8916f481218c449b9759ce017c09Jason Monk @Override 98c2beef51306e8916f481218c449b9759ce017c09Jason Monk protected boolean isLightsOut(int mode) { 993107d99e54795a4fadc5448014ffe2a1f8de7ce3Matthew Ng return super.isLightsOut(mode) || (mAllowAutoDimWallpaperNotVisible && mAutoDim 1003107d99e54795a4fadc5448014ffe2a1f8de7ce3Matthew Ng && !mWallpaperVisible && mode != MODE_WARNING); 1017edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock } 1027edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 10340db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi public LightBarTransitionsController getLightTransitionsController() { 10440db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi return mLightTransitionsController; 10540db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi } 10640db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi 1077edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock @Override 1087edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock protected void onTransition(int oldMode, int newMode, boolean animate) { 1097edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock super.onTransition(oldMode, newMode, animate); 110c2beef51306e8916f481218c449b9759ce017c09Jason Monk applyLightsOut(animate, false /*force*/); 1117edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock } 1127edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 113c2beef51306e8916f481218c449b9759ce017c09Jason Monk private void applyLightsOut(boolean animate, boolean force) { 1147edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock // apply to lights out 115c2beef51306e8916f481218c449b9759ce017c09Jason Monk applyLightsOut(isLightsOut(getMode()), animate, force); 1167edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock } 1177edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 1187edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock private void applyLightsOut(boolean lightsOut, boolean animate, boolean force) { 1197edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock if (!force && lightsOut == mLightsOut) return; 1207edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 1217edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock mLightsOut = lightsOut; 1220e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk if (mNavButtons == null) return; 1237edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 1247edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock // ok, everyone, stop it right there 1250e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk mNavButtons.animate().cancel(); 1267edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 127cdec5ff9f496e345d1e2e40f3d36d66938ace5f6Jason Monk // Bump percentage by 10% if dark. 128cdec5ff9f496e345d1e2e40f3d36d66938ace5f6Jason Monk float darkBump = mLightTransitionsController.getCurrentDarkIntensity() / 10; 129cdec5ff9f496e345d1e2e40f3d36d66938ace5f6Jason Monk final float navButtonsAlpha = lightsOut ? 0.6f + darkBump : 1f; 1307edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 1317edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock if (!animate) { 1320e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk mNavButtons.setAlpha(navButtonsAlpha); 1337edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock } else { 1347edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock final int duration = lightsOut ? LIGHTS_OUT_DURATION : LIGHTS_IN_DURATION; 1350e3aab29ec7d05e58524b454eed2c8ebd64ee4daJason Monk mNavButtons.animate() 1367edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock .alpha(navButtonsAlpha) 1377edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock .setDuration(duration) 1387edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock .start(); 1397edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock } 1407edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock } 1417edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 14240db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi public void reapplyDarkIntensity() { 14340db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi applyDarkIntensity(mLightTransitionsController.getCurrentDarkIntensity()); 14440db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi } 14540db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi 14640db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi public void applyDarkIntensity(float darkIntensity) { 14740db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi SparseArray<ButtonDispatcher> buttonDispatchers = mView.getButtonDispatchers(); 14840db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi for (int i = buttonDispatchers.size() - 1; i >= 0; i--) { 14940db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi buttonDispatchers.valueAt(i).setDarkIntensity(darkIntensity); 15040db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi } 151cdec5ff9f496e345d1e2e40f3d36d66938ace5f6Jason Monk if (mAutoDim) { 152cdec5ff9f496e345d1e2e40f3d36d66938ace5f6Jason Monk applyLightsOut(false, true); 153cdec5ff9f496e345d1e2e40f3d36d66938ace5f6Jason Monk } 154a8f2426df625915553c3d85af8e6241f47fdf160Matthew Ng mView.onDarkIntensityChange(darkIntensity); 15540db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi } 15640db029cfeb263b5b672ca687c347e58ed2ad2aeJorim Jaggi 1577edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock private final View.OnTouchListener mLightsOutListener = new View.OnTouchListener() { 1587edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock @Override 1597edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock public boolean onTouch(View v, MotionEvent ev) { 1607edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock if (ev.getAction() == MotionEvent.ACTION_DOWN) { 1617edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock // even though setting the systemUI visibility below will turn these views 1627edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock // on, we need them to come up faster so that they can catch this motion 1637edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock // event 1647edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock applyLightsOut(false, false, false); 1657edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock 1667edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock try { 16753f28eccc546504cb1e894c02176ecce3139264eAdrian Roos mBarService.setSystemUiVisibility(0, View.SYSTEM_UI_FLAG_LOW_PROFILE, 16853f28eccc546504cb1e894c02176ecce3139264eAdrian Roos "LightsOutListener"); 1697edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock } catch (android.os.RemoteException ex) { 1707edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock } 1717edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock } 1727edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock return false; 1737edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock } 1747edfbca5d00cbc376fda790b50a3fedb9c6070abJohn Spurlock }; 175af638c4f9daa74b4c8e0905f07e11290f6845abeJim Miller} 176