diff options
author | Park Ju Hyung <qkrwngud825@gmail.com> | 2017-01-15 03:33:04 +0900 |
---|---|---|
committer | alk3pInjection <webmaster@raspii.tech> | 2021-09-27 21:17:05 +0800 |
commit | 0b476f959ff10acc9535d0aff8231a3ddda7f021 (patch) | |
tree | 938d5c1fe3540d7fa37d19c39e7501943c836ed1 | |
parent | d662f25af97a2ad03445cd6cca6b1df2e4de627b (diff) |
[ArrowOS][11.0] SystemUI: Implement burn-in protection for status/navbar
Devices with OLED display suffer from
status-bar's notification items and nagivation bar's software keys
causing permanent burn-ins when used long-term.
Moving all items in the area
both horizontally and vertically workarounds this problem.
This new feature can be enabled by setting
config_statusBarBurnInProtection to true.
The shifting interval can be configured with config_shift_interval.
The default shifting interval is 60 seconds.
Forward-ported to oreo-mr1.
* Disable by default.
Change-Id: I8df1ebc8bc0f359fe5a6a1fe11aa6201237a7359
6 files changed, 202 insertions, 0 deletions
diff --git a/packages/SystemUI/res/values/dimens.xml b/packages/SystemUI/res/values/dimens.xml index 73fa77b57911..be2729127fdc 100644 --- a/packages/SystemUI/res/values/dimens.xml +++ b/packages/SystemUI/res/values/dimens.xml @@ -1089,6 +1089,14 @@ <!-- The maximum offset in either direction that icons move to prevent burn-in on AOD. --> <dimen name="default_burn_in_prevention_offset">15dp</dimen> + <!-- The maximum offset in either direction that elements are moved horizontally to prevent + burn-in on status bar and navigation bar. --> + <dimen name="horizontal_max_swift">3.0dp</dimen> + + <!-- The maximum offset in either direction that elements are moved vertically to prevent + burn-in on status bar and navigation bar. --> + <dimen name="vertical_max_swift">1.0dp</dimen> + <dimen name="corner_size">8dp</dimen> <dimen name="top_padding">0dp</dimen> <dimen name="bottom_padding">48dp</dimen> diff --git a/packages/SystemUI/res/values/lineage_config.xml b/packages/SystemUI/res/values/lineage_config.xml index b17044b1bcc6..d77e7e82821e 100644 --- a/packages/SystemUI/res/values/lineage_config.xml +++ b/packages/SystemUI/res/values/lineage_config.xml @@ -34,4 +34,13 @@ <!-- Whether usage of the proximity sensor during doze is supported --> <bool name="doze_proximity_sensor_supported">true</bool> + + <!-- Whether to enable shifting of elements in the status bar and the navigation bar. + Should be enabled for OLED devices to reduce/prevent burn in on the status bar + and on the navigation bar and disabled for all other devices. --> + <bool name="config_statusBarBurnInProtection">false</bool> + + <!-- Amount of time in seconds to wait before shifting elements around when the burn in + protection is enabled for status bar and navigation bar --> + <integer name="config_shift_interval">60</integer> </resources> diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java index e28abe4e7e00..c591f3a05d77 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java @@ -178,6 +178,13 @@ public class NavigationBarView extends FrameLayout implements private boolean mShowCursorKeys; + private int mBasePaddingBottom; + private int mBasePaddingLeft; + private int mBasePaddingRight; + private int mBasePaddingTop; + + private ViewGroup mNavigationBarContents; + private class NavTransitionListener implements TransitionListener { private boolean mBackTransitioning; private boolean mHomeAppearing; @@ -938,6 +945,18 @@ public class NavigationBarView extends FrameLayout implements mRecentsOnboarding.hide(true); } + public void swiftNavigationBarItems(int horizontalShift, int verticalShift) { + if (mNavigationBarContents == null) { + return; + } + + mNavigationBarContents.setPaddingRelative(mBasePaddingLeft + horizontalShift, + mBasePaddingTop + verticalShift, + mBasePaddingRight + horizontalShift, + mBasePaddingBottom - verticalShift); + invalidate(); + } + @Override public void onFinishInflate() { super.onFinishInflate(); @@ -948,6 +967,14 @@ public class NavigationBarView extends FrameLayout implements Divider divider = Dependency.get(Divider.class); divider.registerInSplitScreenListener(mDockedListener); + + mNavigationBarContents = (ViewGroup) findViewById(R.id.nav_buttons); + + mBasePaddingLeft = mNavigationBarContents.getPaddingStart(); + mBasePaddingTop = mNavigationBarContents.getPaddingTop(); + mBasePaddingRight = mNavigationBarContents.getPaddingEnd(); + mBasePaddingBottom = mNavigationBarContents.getPaddingBottom(); + updateOrientationViews(); reloadNavIcons(); } diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBarView.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBarView.java index 8856d892fcfb..c96c4e712585 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBarView.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBarView.java @@ -23,6 +23,7 @@ import static java.lang.Float.isNaN; import android.annotation.Nullable; import android.content.Context; import android.content.res.Configuration; +import android.content.res.Resources; import android.graphics.Rect; import android.os.RemoteException; import android.util.AttributeSet; @@ -59,6 +60,13 @@ public class PhoneStatusBarView extends PanelBar implements Callbacks { private static final boolean DEBUG_GESTURES = false; private final CommandQueue mCommandQueue; + private int mBasePaddingBottom; + private int mBasePaddingLeft; + private int mBasePaddingRight; + private int mBasePaddingTop; + + private ViewGroup mStatusBarContents; + StatusBar mBar; boolean mIsFullyOpenedPanel = false; @@ -131,11 +139,29 @@ public class PhoneStatusBarView extends PanelBar implements Callbacks { mScrimController = scrimController; } + public void swiftStatusBarItems(int horizontalShift, int verticalShift) { + if (mStatusBarContents == null) { + return; + } + + mStatusBarContents.setPaddingRelative(mBasePaddingLeft + horizontalShift, + mBasePaddingTop + verticalShift, + mBasePaddingRight + horizontalShift, + mBasePaddingBottom - verticalShift); + invalidate(); + } + @Override public void onFinishInflate() { mBattery = findViewById(R.id.battery); mCutoutSpace = findViewById(R.id.cutout_space_view); mCenterIconSpace = findViewById(R.id.centered_icon_area); + mStatusBarContents = (ViewGroup) findViewById(R.id.status_bar_contents); + + mBasePaddingLeft = mStatusBarContents.getPaddingStart(); + mBasePaddingTop = mStatusBarContents.getPaddingTop(); + mBasePaddingRight = mStatusBarContents.getPaddingEnd(); + mBasePaddingBottom = mStatusBarContents.getPaddingBottom(); updateResources(); } diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java index 8aca0846a678..81636518a2c5 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java @@ -221,6 +221,7 @@ import com.android.systemui.statusbar.phone.dagger.StatusBarComponent; import com.android.systemui.statusbar.phone.dagger.StatusBarPhoneModule; import com.android.systemui.statusbar.policy.BatteryController; import com.android.systemui.statusbar.policy.BrightnessMirrorController; +import com.android.systemui.statusbar.policy.BurnInProtectionController; import com.android.systemui.statusbar.policy.ConfigurationController; import com.android.systemui.statusbar.policy.ConfigurationController.ConfigurationListener; import com.android.systemui.statusbar.policy.DeviceProvisionedController; @@ -369,6 +370,7 @@ public class StatusBar extends SystemUI implements DemoMode, private final AutoHideController mAutoHideController; @Nullable private final KeyguardLiftController mKeyguardLiftController; + private BurnInProtectionController mBurnInProtectionController; private final Point mCurrentDisplaySize = new Point(); @@ -1189,6 +1191,8 @@ public class StatusBar extends SystemUI implements DemoMode, mStatusBarView.findViewById(R.id.notification_lights_out)); mNotificationShadeWindowViewController.setStatusBarView(mStatusBarView); checkBarModes(); + mBurnInProtectionController = + new BurnInProtectionController(mContext, this, mStatusBarView); }).getFragmentManager() .beginTransaction() .replace(R.id.status_bar_container, new CollapsedStatusBarFragment(), @@ -4005,6 +4009,10 @@ public class StatusBar extends SystemUI implements DemoMode, updateNotificationPanelTouchState(); mNotificationShadeWindowViewController.cancelCurrentTouch(); + + if (mBurnInProtectionController != null) { + mBurnInProtectionController.stopSwiftTimer(); + } if (mLaunchCameraOnFinishedGoingToSleep) { mLaunchCameraOnFinishedGoingToSleep = false; @@ -4060,6 +4068,9 @@ public class StatusBar extends SystemUI implements DemoMode, mLaunchCameraWhenFinishedWaking = false; } updateScrimController(); + if (mBurnInProtectionController != null) { + mBurnInProtectionController.startSwiftTimer(); + } } }; diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/BurnInProtectionController.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/BurnInProtectionController.java new file mode 100644 index 000000000000..cf24bf72d0a1 --- /dev/null +++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/BurnInProtectionController.java @@ -0,0 +1,121 @@ +/* + * Copyright 2017-2018 Paranoid Android + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.systemui.statusbar.policy; + +import android.content.Context; +import android.content.res.Resources; +import android.os.Handler; +import android.os.Looper; +import android.util.Log; +import android.view.View; + +import com.android.systemui.R; +import com.android.systemui.statusbar.phone.PhoneStatusBarView; +import com.android.systemui.statusbar.phone.NavigationBarView; +import com.android.systemui.statusbar.phone.StatusBar; + +import java.util.Timer; +import java.util.TimerTask; + +public class BurnInProtectionController { + + private static final String TAG = BurnInProtectionController.class.getSimpleName(); + private static final boolean DEBUG = false; + + private boolean mSwiftEnabled; + private int mHorizontalShift = 0; + private int mVerticalShift = 0; + private int mHorizontalDirection = 1; + private int mVerticalDirection = 1; + private int mNavigationBarHorizontalMaxShift; + private int mNavigationBarVerticalMaxShift; + private int mHorizontalMaxShift; + private int mVerticalMaxShift; + private long mShiftInterval; + + private Timer mTimer; + + private StatusBar mStatusBar; + private PhoneStatusBarView mPhoneStatusBarView; + + private Context mContext; + + public BurnInProtectionController(Context context, StatusBar statusBar, + PhoneStatusBarView phoneStatusBarView) { + mContext = context; + + mStatusBar = statusBar; + + mPhoneStatusBarView = phoneStatusBarView; + + mSwiftEnabled = mContext.getResources().getBoolean( + R.bool.config_statusBarBurnInProtection); + mHorizontalMaxShift = mContext.getResources() + .getDimensionPixelSize(R.dimen.horizontal_max_swift); + // total of ((vertical_max_swift - 1) * 2) pixels can be moved + mVerticalMaxShift = mContext.getResources() + .getDimensionPixelSize(R.dimen.vertical_max_swift) - 1; + mShiftInterval = (long) mContext.getResources().getInteger(R.integer.config_shift_interval); + } + + public void startSwiftTimer() { + if (!mSwiftEnabled) return; + if (mTimer == null) { + mTimer = new Timer(); + } + mTimer.schedule(new TimerTask() { + @Override + public void run() { + final Handler mUiHandler = new Handler(Looper.getMainLooper()); + mUiHandler.post(() -> { + swiftItems(); + }); + } + }, 0, mShiftInterval * 1000); + if (DEBUG) Log.d(TAG, "Started swift timer"); + } + + public void stopSwiftTimer() { + if (!mSwiftEnabled) return; + mTimer.cancel(); + mTimer.purge(); + mTimer = null; + if (DEBUG) Log.d(TAG, "Canceled swift timer"); + } + + private void swiftItems() { + mHorizontalShift += mHorizontalDirection; + if ((mHorizontalShift >= mHorizontalMaxShift) || + (mHorizontalShift <= -mHorizontalMaxShift)) { + mHorizontalDirection *= -1; + } + + mVerticalShift += mVerticalDirection; + if ((mVerticalShift >= mVerticalMaxShift) || + (mVerticalShift <= -mVerticalMaxShift)) { + mVerticalDirection *= -1; + } + + mPhoneStatusBarView.swiftStatusBarItems(mHorizontalShift, mVerticalShift); + NavigationBarView mNavigationBarView = mStatusBar.getNavigationBarView(); + if (mNavigationBarView != null) { + mNavigationBarView.swiftNavigationBarItems(mHorizontalShift, mVerticalShift); + } + + if (DEBUG) Log.d(TAG, "Swifting items.."); + } +} |