Android P自動背光原理

目錄:
1,sensor 基本架構圖
2,Lsensor UI 手動設定
3,Lsensor 自動算法

關鍵詞:
lux : 環(huán)境光線
nit: 屏幕亮度
backlight:UI 中設定進度條顯示數字

1-sensor 基本架構圖
Light sensor 屬于sensor 其中的一個設備, 因此架構都一樣,light sensor 有I2C 接口,spi 接口,要從硬件上選擇一種就可以, 最好選擇I2C , 進行i2c通信就可以獲取lux 值

圖片.png

Lsensor 數據獲取步驟(獲取lux 可定制開發(fā)app)
Setp0:獲取傳獲取傳感器對象
Setp1:感器管理器對象
Setp2:定義事件監(jiān)聽器-----》下面有給出在原生code 中獲取lux(onSensorChanged)
Setp3:注冊事件監(jiān)聽器
Setp4:卸載事件監(jiān)聽器

圖片.png

2,Lsensor UI 手動設定
在原生android P code 中,亮度的調節(jié)分為三中方式

1) 在設置中手動設定亮度方式

2) 在system UI 中手動設定亮度

3) 在播放視頻時候設定亮度

上面的幾種方式最后調用都到了updatePowerState(), 手動更改亮度,對自動亮度的調整有影響

2.1 System UI , 設置中進行了設定亮度

frameworks/base/packages/SystemUI/src/com/android/systemui/settings/BrightnessController.java
圖片.png

最后背光的修改都要走到下面的函數

frameworks/base/services/core/java/com/android/server/display/DisplayPowerController.java
private void animateScreenBrightness(int target, int rate) {……….}

3,Lsensor 自動算法
基本思路:
Stetp 1:創(chuàng)建三條曲線 lux---nits---backlight

mNitsToBacklightSpline = Spline.createSpline(nits, normalizedBacklight);
mBacklightToNitsSpline = Spline.createSpline(normalizedBacklight, nits);
mBrightnessSpline = Spline.createSpline(lux, nits);----->最重要的曲線, lux-->nits (由nits->bightlight)

Step 2:
手動調整了亮度-> addUserDataPoint(float lux, float brightness) ->重新調整曲線(mBrightnessSpline = Spline.createSpline(lux, nits))--->記錄用戶調整值,根據用戶的習慣,重新擬合曲線

Step 3:
最后調用animateScreenBrightness,這里利用設定背光時間rate,逐步更新,達到不閃爍

3.1 code 流程
創(chuàng)建曲線:

frameworks/base/services/core/java/com/android/server/display/DisplayPowerController.java
frameworks/base/services/core/java/com/android/server/display/BrightnessMappingStrategy.java
public DisplayPowerController(Context context,
        DisplayPowerCallbacks callbacks, Handler handler,SensorManager sensorManager, DisplayBlanker blanker) {
      mBrightnessMapper = BrightnessMappingStrategy.create(resources);
}

下面都是制造商的配置數組, 然后根據配置建立樣條曲線

int[] brightnessLevelsBacklight---->config_autoBrightnessLcdBacklightValues
float[] luxLevels------------------>config_autoBrightnessLevels
float[] brightnessLevelsNits------->config_autoBrightnessDisplayValuesNits
float[] nitsRange------------------>config_screenBrightnessNits
int[] backlightRange -------------->config_screenBrightnessBacklight
圖片.png
mBrightnessSpline = Spline.createSpline(lux, nits);

用戶手動調整了亮度:

frameworks/base/services/core/java/com/android/server/display/DisplayPowerController.java
frameworks/base/services/core/java/com/android/server/display/AutomaticBrightnessController.java
DisplayPowerController--> BrightnessMappingStrategy.create()-?AutomaticBrightnessController-----> mAutomaticBrightnessController.configure
圖片.png

下圖進行了對比,默認曲線有用戶調整后曲線的情況:


圖片.png

問題:什么時候用戶清除配置,reset 動作 (感覺nrea 不需要考慮)
1, 切換用戶
2, BrightnessConfigure 重新配置
3, 屏幕由交互狀態(tài)進入非交互狀態(tài)時,這個是有display 狀態(tài)決定

3.2 animateScreenBrightness 分析

有上面可以知道event 攜帶參數lux ,根據lux (利用擬合曲線)算出backlight 值,最后由animateScreenBrightness(int target, int rate)函數進行更新,在參數中就有目標target, 更新rate (分fast,slow)。
如果rate = 0 ,直接更新,可能閃屏。
如果rate > 0 ,根據rate 速度逐步進行更新背光值

frameworks/base/services/core/java/com/android/server/display/DisplayPowerController.java

rate 配置:


圖片.png

更新目標背光流程:

animateScreenBrightness-->mScreenBrightnessRampAnimator.animateTo(target, rate)--->postAnimationCallback();--->mAnimationCallback-->mProperty.setValue(mObject, mCurrentValue);--->

最后走到了:DisplayPowerState.java: setValue-->setScreenBrightness


圖片.png
frameworks/base/services/core/java/com/android/server/display/DisplayPowerState.java:
圖片.png
最后編輯于
?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
【社區(qū)內容提示】社區(qū)部分內容疑似由AI輔助生成,瀏覽時請結合常識與多方信息審慎甄別。
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發(fā)布,文章內容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關閱讀更多精彩內容

友情鏈接更多精彩內容