日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > Android >内容正文

Android

Android7.0 PowerManagerService亮灭屏分析(三)

發(fā)布時間:2025/3/15 Android 19 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Android7.0 PowerManagerService亮灭屏分析(三) 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

在前面兩部分已經(jīng)對繪制windows與設置設備狀態(tài)進行了詳細講解. 之后接著就該對亮度值進行設置, 實現(xiàn)亮屏動作了.

在DisplayPowerController中的animateScreenBrightness函數(shù)通過亮度漸變動畫來將亮度設置到目標亮度.

[java]?view plain?copy
  • //?Brightness?animation?ramp?rate?in?brightness?units?per?second.??
  • private?static?final?int?BRIGHTNESS_RAMP_RATE_SLOW?=?40;?????//亮度漸變動畫較慢的速率,?每秒變化40個亮度單位???
  • ??
  • ????mBrightnessRampRateFast?=?resources.getInteger(??
  • ????????????com.android.internal.R.integer.config_brightness_ramp_rate_fast);???//從配置文件中獲取較快的亮度速率??
  • ??
  • ????//?Animate?the?screen?brightness?when?the?screen?is?on?or?dozing.??
  • ????//?Skip?the?animation?when?the?screen?is?off?or?suspended.??
  • ????if?(!mPendingScreenOff)?{??
  • ????????if?(state?==?Display.STATE_ON?||?state?==?Display.STATE_DOZE)?{??
  • ????????????animateScreenBrightness(brightness,??????//當亮屏或doze狀態(tài)時有亮度漸變動畫??
  • ????????????????????slowChange???BRIGHTNESS_RAMP_RATE_SLOW?:?mBrightnessRampRateFast);??
  • ????????}?else?{??
  • ????????????animateScreenBrightness(brightness,?0);???//滅屏時沒有亮度漸變動畫,直接將亮度設置為0??
  • ????????}??
  • ????}??
  • 在animateScreenBrightness函數(shù)中調(diào)用動畫mScreenBrightnessRampAnimator對亮度值處理, 而mScreenBrightnessRampAnimator是在initialize()函數(shù)中進行初始化的, 在構(gòu)造函數(shù)中將DisplayPowerState和DisplayPowerState.SCREEN_BRIGHTNESS傳輸過去.

    [java]?view plain?copy
  • ??private?void?initialize()?{??
  • ??????//....??
  • ????????mScreenBrightnessRampAnimator?=?new?RampAnimator<DisplayPowerState>(??//泛型為DisplayPowerState??
  • ????????????????mPowerState,?DisplayPowerState.SCREEN_BRIGHTNESS);??
  • ????????mScreenBrightnessRampAnimator.setListener(mRampAnimatorListener);??
  • ?????//...??
  • }??
  • ??
  • ????private?void?animateScreenBrightness(int?target,?int?rate)?{??
  • ????????if?(DEBUG)?{??
  • ????????????Slog.d(TAG,?"Animating?brightness:?target="?+?target?+",?rate="?+?rate);??
  • ????????}??
  • ????????if?(mScreenBrightnessRampAnimator.animateTo(target,?rate))?{????//動畫處理亮度值??
  • ????????????try?{??
  • ????????????????mBatteryStats.noteScreenBrightness(target);??
  • ????????????}?catch?(RemoteException?ex)?{??
  • ????????????????//?same?process??
  • ????????????}??
  • ????????}??
  • ????}??
  • 在RampAnimator的構(gòu)造函數(shù)中將DisplayPowerState賦值給mObject,?DisplayPowerState.SCREEN_BRIGHTNESS賦值給mProperty, 并且創(chuàng)建mChoreographer實例.

    [java]?view plain?copy
  • public?RampAnimator(T?object,?IntProperty<T>?property)?{??
  • ????mObject?=?object;??
  • ????mProperty?=?property;??
  • ????mChoreographer?=?Choreographer.getInstance();??
  • }??
  • 下面重點講解animateTo函數(shù).

    [java]?view plain?copy
  • public?boolean?animateTo(int?target,?int?rate)?{??
  • ????//?Immediately?jump?to?the?target?the?first?time.??
  • ????if?(mFirstTime?||?rate?<=?0)?{???//當?shù)谝淮握{(diào)用animateTo,?或者rate小于等于0時直接設置目標亮度.??
  • ????????if?(mFirstTime?||?target?!=?mCurrentValue)?{??
  • ????????????mFirstTime?=?false;???//之后就不是第一次調(diào)用該函數(shù)??
  • ????????????mRate?=?0;??????????????//設置mRate為0??
  • ????????????mTargetValue?=?target;???//設置目標亮度為target??
  • ????????????mCurrentValue?=?target;??
  • ????????????mProperty.setValue(mObject,?target);???//調(diào)用DisplayPowerState.SCREEN_BRIGHTNESS設置亮度值??
  • ????????????if?(mAnimating)?{??
  • ????????????????mAnimating?=?false;??
  • ????????????????cancelAnimationCallback();??
  • ????????????}??
  • ????????????if?(mListener?!=?null)?{??
  • ????????????????mListener.onAnimationEnd();??//動畫結(jié)束??
  • ????????????}??
  • ????????????return?true;??
  • ????????}??
  • ????????return?false;??
  • ????}??
  • ??
  • ????//?Adjust?the?rate?based?on?the?closest?target.??
  • ????//?If?a?faster?rate?is?specified,?then?use?the?new?rate?so?that?we?converge??
  • ????//?more?rapidly?based?on?the?new?request.??
  • ????//?If?a?slower?rate?is?specified,?then?use?the?new?rate?only?if?the?current??
  • ????//?value?is?somewhere?in?between?the?new?and?the?old?target?meaning?that??
  • ????//?we?will?be?ramping?in?a?different?direction?to?get?there.??
  • ????//?Otherwise,?continue?at?the?previous?rate.??
  • ????if?(!mAnimating??
  • ????????????||?rate?>?mRate??
  • ????????????||?(target?<=?mCurrentValue?&&?mCurrentValue?<=?mTargetValue)??
  • ????????????||?(mTargetValue?<=?mCurrentValue?&&?mCurrentValue?<=?target))?{??
  • ????????mRate?=?rate;???//重新調(diào)節(jié)亮度速率??
  • ????}??
  • ??
  • ????final?boolean?changed?=?(mTargetValue?!=?target);??//如果當前亮度值不等于目標亮度值,說明亮度改變了??
  • ????mTargetValue?=?target;????//重新設置mTargetValue??
  • ??
  • ????//?Start?animating.??開始動畫??
  • ????if?(!mAnimating?&&?target?!=?mCurrentValue)?{????
  • ????????mAnimating?=?true;??
  • ????????mAnimatedValue?=?mCurrentValue;??
  • ????????mLastFrameTimeNanos?=?System.nanoTime();??
  • ????????postAnimationCallback();??
  • ????}??
  • ??
  • ????return?changed;???
  • }??
  • 在postAnimationCallback中調(diào)用Choreographer的postCallback函數(shù)處理, 調(diào)用完成后回調(diào)回mAnimationCallback的run函數(shù)

    [java]?view plain?copy
  • private?void?postAnimationCallback()?{??
  • ????mChoreographer.postCallback(Choreographer.CALLBACK_ANIMATION,?mAnimationCallback,?null);??
  • }??
  • ??
  • private?final?Runnable?mAnimationCallback?=?new?Runnable()?{??
  • ????@Override?//?Choreographer?callback??
  • ????public?void?run()?{??
  • ????????final?long?frameTimeNanos?=?mChoreographer.getFrameTimeNanos();??
  • ????????final?float?timeDelta?=?(frameTimeNanos?-?mLastFrameTimeNanos)??
  • ????????????????*?0.000000001f;??
  • ????????mLastFrameTimeNanos?=?frameTimeNanos;??//記錄最后一次的frameTimeNanos??
  • ??
  • ????????//?Advance?the?animated?value?towards?the?target?at?the?specified?rate??
  • ????????//?and?clamp?to?the?target.?This?gives?us?the?new?current?value?but??
  • ????????//?we?keep?the?animated?value?around?to?allow?for?fractional?increments??
  • ????????//?towards?the?target.??
  • ????????final?float?scale?=?ValueAnimator.getDurationScale();??
  • ????????if?(scale?==?0)?{??
  • ????????????//?Animation?off.??
  • ????????????mAnimatedValue?=?mTargetValue;???//讓scale為0時,?表示動畫停止了,?將mAnimatedValue設置為目標亮度??
  • ????????}?else?{??
  • ????????????final?float?amount?=?timeDelta?*?mRate?/?scale;??//計算每一次需要變化的亮度值??
  • ????????????if?(mTargetValue?>?mCurrentValue)?{??
  • ????????????????mAnimatedValue?=?Math.min(mAnimatedValue?+?amount,?mTargetValue);??//亮屏,每次增加亮度amount,不超過目標亮度??
  • ????????????}?else?{??
  • ????????????????mAnimatedValue?=?Math.max(mAnimatedValue?-?amount,?mTargetValue);?//暗屏,?每次減少amount個亮度,?不超過目標亮度??
  • ????????????}??
  • ????????}??
  • ????????final?int?oldCurrentValue?=?mCurrentValue;??
  • ????????mCurrentValue?=?Math.round(mAnimatedValue);??//獲取當前要達到的亮度值??
  • ??
  • ????????if?(oldCurrentValue?!=?mCurrentValue)?{??
  • ????????????mProperty.setValue(mObject,?mCurrentValue);??//調(diào)用DisplayPowerState.SCREEN_BRIGHTNESS設置亮度值??
  • ????????}??
  • ??
  • ????????if?(mTargetValue?!=?mCurrentValue)?{??
  • ????????????postAnimationCallback();???//如果還沒有達到目標亮度,就會繼續(xù)調(diào)用postAnimationCallback循環(huán)設置亮度值??
  • ????????}?else?{??
  • ????????????mAnimating?=?false;??
  • ????????????if?(mListener?!=?null)?{??
  • ????????????????mListener.onAnimationEnd();??//否則,亮度動畫結(jié)束??
  • ????????????}??
  • ????????}??
  • ????}??
  • };??
  • DisplayPowerState.SCREEN_BRIGHTNESS的setValue函數(shù)是在DisplayPowerState中實現(xiàn)的.

    [java]?view plain?copy
  • public?static?final?IntProperty<DisplayPowerState>?SCREEN_BRIGHTNESS?=??
  • ????????new?IntProperty<DisplayPowerState>("screenBrightness")?{??
  • ????@Override??
  • ????public?void?setValue(DisplayPowerState?object,?int?value)?{??
  • ????????object.setScreenBrightness(value);??//調(diào)用DisplayPowerState的setScreenBrightness函數(shù),設置亮度值??
  • ????}??
  • ??
  • ????@Override??
  • ????public?Integer?get(DisplayPowerState?object)?{??
  • ????????return?object.getScreenBrightness();??
  • ????}??
  • };??
  • ??
  • public?void?setScreenBrightness(int?brightness)?{??
  • ????if?(mScreenBrightness?!=?brightness)?{??
  • ????????if?(DEBUG)?{??
  • ????????????Slog.d(TAG,?"setScreenBrightness:?brightness="?+?brightness);??
  • ????????}??
  • ??
  • ????????mScreenBrightness?=?brightness;??//設置全局的亮度值??
  • ????????if?(mScreenState?!=?Display.STATE_OFF)?{??
  • ????????????mScreenReady?=?false;??
  • ????????????scheduleScreenUpdate();???//如果不是滅屏狀態(tài),更新屏幕狀態(tài)??
  • ????????}??
  • ????}??
  • }??
  • scheduleScreenUpdate函數(shù)最終通過Handler發(fā)送mScreenUpdateRunnable對象來更新亮度值. 從run函數(shù)中可以看出只有當mColorFadeLevel > 0f時才能給brightness設置亮度值, 所以說當windows沒有繪制完成時就算mScreenBrightness有值不為0, 但是brightness仍然為0不能點亮屏幕.

    [java]?view plain?copy
  • private?final?Runnable?mScreenUpdateRunnable?=?new?Runnable()?{??
  • ????@Override??
  • ????public?void?run()?{??
  • ????????mScreenUpdatePending?=?false;??
  • ??
  • ????????int?brightness?=?mScreenState?!=?Display.STATE_OFF??
  • ????????????????&&?mColorFadeLevel?>?0f???mScreenBrightness?:?0;????//判斷設置亮度值??
  • ????????if?(mPhotonicModulator.setState(mScreenState,?brightness))?{??
  • ????????????if?(DEBUG)?{??
  • ????????????????Slog.d(TAG,?"Screen?ready");??
  • ????????????}??
  • ????????????mScreenReady?=?true;??
  • ????????????invokeCleanListenerIfNeeded();??
  • ????????}?else?{??
  • ????????????if?(DEBUG)?{??
  • ????????????????Slog.d(TAG,?"Screen?not?ready");??
  • ????????????}??
  • ????????}??
  • ????}??
  • };??
  • 之后的流程就與設置設置狀態(tài)的流程相同了, 調(diào)用DisplayManagerService中DisplayBlanker的requestDisplayState函數(shù).

    [java]?view plain?copy
  • DisplayBlanker?blanker?=?new?DisplayBlanker()?{??
  • ????@Override??
  • ????public?void?requestDisplayState(int?state,?int?brightness)?{??
  • ????????//?The?order?of?operations?is?important?for?legacy?reasons.??
  • ????????if?(state?==?Display.STATE_OFF)?{??
  • ????????????requestGlobalDisplayStateInternal(state,?brightness);??
  • ????????}??
  • ??
  • ????????callbacks.onDisplayStateChange(state);??????
  • ??
  • ????????if?(state?!=?Display.STATE_OFF)?{??
  • ????????????requestGlobalDisplayStateInternal(state,?brightness);??//亮屏調(diào)用設置狀態(tài),亮度??
  • ????????}??
  • ????}??
  • };??
  • [java]?view plain?copy
  • private?void?requestGlobalDisplayStateInternal(int?state,?int?brightness)?{??
  • ????if?(state?==?Display.STATE_UNKNOWN)?{??
  • ????????state?=?Display.STATE_ON;??
  • ????}??
  • ????if?(state?==?Display.STATE_OFF)?{??
  • ????????brightness?=?PowerManager.BRIGHTNESS_OFF;??//滅屏設置屏幕亮度為0??
  • ????}?else?if?(brightness?<?0)?{??
  • ????????brightness?=?PowerManager.BRIGHTNESS_DEFAULT;??//屏幕亮度小于0,設置為默認亮度??
  • ????}?else?if?(brightness?>?PowerManager.BRIGHTNESS_ON)?{??
  • ????????brightness?=?PowerManager.BRIGHTNESS_ON;????//屏幕亮度大于255設置最大亮度值255??
  • ????}??
  • ??
  • ????synchronized?(mTempDisplayStateWorkQueue)?{??
  • ????????try?{??
  • ????????????//?Update?the?display?state?within?the?lock.??
  • ????????????//?Note?that?we?do?not?need?to?schedule?traversals?here?although?it??
  • ????????????//?may?happen?as?a?side-effect?of?displays?changing?state.??
  • ????????????synchronized?(mSyncRoot)?{??
  • ????????????????if?(mGlobalDisplayState?==?state??
  • ????????????????????????&&?mGlobalDisplayBrightness?==?brightness)?{??
  • ????????????????????return;?//?no?change?????亮度與狀態(tài)都沒有改變就return??
  • ????????????????}??
  • ??
  • ????????????????Trace.traceBegin(Trace.TRACE_TAG_POWER,?"requestGlobalDisplayState("??
  • ????????????????????????+?Display.stateToString(state)??
  • ????????????????????????+?",?brightness="?+?brightness?+?")");??
  • ????????????????mGlobalDisplayState?=?state;??
  • ????????????????mGlobalDisplayBrightness?=?brightness;??
  • ????????????????applyGlobalDisplayStateLocked(mTempDisplayStateWorkQueue);???//應用全局狀態(tài)??
  • ????????????}??
  • ??
  • ????????????//?Setting?the?display?power?state?can?take?hundreds?of?milliseconds??
  • ????????????//?to?complete?so?we?defer?the?most?expensive?part?of?the?work?until??
  • ????????????//?after?we?have?exited?the?critical?section?to?avoid?blocking?other??
  • ????????????//?threads?for?a?long?time.??
  • ????????????for?(int?i?=?0;?i?<?mTempDisplayStateWorkQueue.size();?i++)?{??
  • ????????????????mTempDisplayStateWorkQueue.get(i).run();??//運行mTempDisplayStateWorkQueue隊列中的runnable??
  • ????????????}??
  • ????????????Trace.traceEnd(Trace.TRACE_TAG_POWER);??
  • ????????}?finally?{??
  • ????????????mTempDisplayStateWorkQueue.clear();??
  • ????????}??
  • ????}??
  • }??
  • 在applyGlobalDisplayStateLocked函數(shù)中獲取所有的devices, 調(diào)用對應設備的requestDisplayStateLocked函數(shù)更新請求狀態(tài). 啟動devices為LocalDisplayAdapter, 就會調(diào)用到該類的requestDisplayStateLocked獲得runnable.
    [java]?view plain?copy
  • private?void?applyGlobalDisplayStateLocked(List<Runnable>?workQueue)?{??
  • ????final?int?count?=?mDisplayDevices.size();??
  • ????for?(int?i?=?0;?i?<?count;?i++)?{???//遍歷devices??
  • ????????DisplayDevice?device?=?mDisplayDevices.get(i);??
  • ????????Runnable?runnable?=?updateDisplayStateLocked(device);??//獲得devices中的runnable??
  • ????????if?(runnable?!=?null)?{??
  • ????????????workQueue.add(runnable);??//將runnable加入workQueue隊列,?即mTempDisplayStateWorkQueue隊列??
  • ????????}??
  • ????}??
  • }??
  • ??
  • private?Runnable?updateDisplayStateLocked(DisplayDevice?device)?{??
  • ????//?Blank?or?unblank?the?display?immediately?to?match?the?state?requested??
  • ????//?by?the?display?power?controller?(if?known).??
  • ????DisplayDeviceInfo?info?=?device.getDisplayDeviceInfoLocked();??//獲取devices信息??
  • ????if?((info.flags?&?DisplayDeviceInfo.FLAG_NEVER_BLANK)?==?0)?{??
  • ????????return?device.requestDisplayStateLocked(mGlobalDisplayState,?mGlobalDisplayBrightness);?//調(diào)用requestDisplayStateLocked函數(shù)??
  • ????}??
  • ????return?null;??
  • }??
  • 在requestDisplayStateLocked中主要的任務就是創(chuàng)建一個runnable返回到DisplayManagerService中,并且等待回調(diào)run函數(shù).

    [java]?view plain?copy
  • @Override??
  • public?Runnable?requestDisplayStateLocked(final?int?state,?final?int?brightness)?{??
  • ????//?Assume?that?the?brightness?is?off?if?the?display?is?being?turned?off.??
  • ????assert?state?!=?Display.STATE_OFF?||?brightness?==?PowerManager.BRIGHTNESS_OFF;??
  • ??
  • ????final?boolean?stateChanged?=?(mState?!=?state);??//狀態(tài)是否改變??
  • ????final?boolean?brightnessChanged?=?(mBrightness?!=?brightness)?&&?mBacklight?!=?null;??//亮度值是否改變??
  • ????if?(stateChanged?||?brightnessChanged)?{??//如果亮度值或者亮度狀態(tài)發(fā)生改變就重新設置對應值??
  • ????????final?int?displayId?=?mBuiltInDisplayId;??
  • ????????final?IBinder?token?=?getDisplayTokenLocked();??
  • ????????final?int?oldState?=?mState;??
  • ??
  • ????????if?(stateChanged)?{???//設置亮度時.狀態(tài)已經(jīng)設置好,無變化??
  • ????????????mState?=?state;??
  • ????????????updateDeviceInfoLocked();??
  • ????????}??
  • ??
  • ????????if?(brightnessChanged)?{??
  • ????????????mBrightness?=?brightness;??//設置mBrightness??
  • ????????}??
  • ??
  • ????????//?Defer?actually?setting?the?display?state?until?after?we?have?exited??
  • ????????//?the?critical?section?since?it?can?take?hundreds?of?milliseconds??
  • ????????//?to?complete.??
  • ????????return?new?Runnable()?{????//新建一個runnable返回??
  • ????????????@Override??
  • ????????????public?void?run()?{??//在DisplayManagerService中調(diào)用run函數(shù)??
  • ????????????????//?Exit?a?suspended?state?before?making?any?changes.????
  • ????????????????int?currentState?=?oldState;??
  • ????????????????if?(Display.isSuspendedState(oldState)????//判斷設置是否還是在suspend狀態(tài)??
  • ????????????????????????||?oldState?==?Display.STATE_UNKNOWN)?{??
  • ????????????????????if?(!Display.isSuspendedState(state))?{??
  • ????????????????????????setDisplayState(state);??
  • ????????????????????????currentState?=?state;??
  • ????????????????????}?else?if?(state?==?Display.STATE_DOZE_SUSPEND??
  • ????????????????????????????||?oldState?==?Display.STATE_DOZE_SUSPEND)?{??
  • ????????????????????????setDisplayState(Display.STATE_DOZE);??
  • ????????????????????????currentState?=?Display.STATE_DOZE;??
  • ????????????????????}?else?{??
  • ????????????????????????return;?//?old?state?and?new?state?is?off??
  • ????????????????????}??
  • ????????????????}??
  • ??
  • ????????????????//?Apply?brightness?changes?given?that?we?are?in?a?non-suspended?state.??
  • ????????????????if?(brightnessChanged)?{??
  • ????????????????????if?(isPowerDebug())?{??
  • ????????????????????????Slog.d(TAG,?"set?display?brightness="?+?brightness);??
  • ????????????????????}??
  • ????????????????????setDisplayBrightness(brightness);????//設置屏幕亮度??
  • ????????????????}??
  • ??
  • ????????????????//?Enter?the?final?desired?state,?possibly?suspended.??
  • ????????????????if?(state?!=?currentState)?{??
  • ????????????????????if(isPowerDebug())?{??
  • ????????????????????????Slog.d(TAG,?"set?display?state="?+?state);??
  • ????????????????????}??
  • ????????????????????setDisplayState(state);??
  • ????????????????}??
  • ????????????}??
  • [java]?view plain?copy
  • ????????????private?void?setDisplayBrightness(int?brightness)?{??
  • ????????????????if?(DEBUG)?{??
  • ????????????????????Slog.d(TAG,?"setDisplayBrightness("??
  • ????????????????????????????+?"id="?+?displayId?+?",?brightness="?+?brightness?+?")");??
  • ????????????????}??
  • ??
  • ????????????????Trace.traceBegin(Trace.TRACE_TAG_POWER,?"setDisplayBrightness("??
  • ????????????????????????+?"id="?+?displayId?+?",?brightness="?+?brightness?+?")");??
  • ????????????????try?{??
  • ????????????????????mBacklight.setBrightness(brightness);???//調(diào)用LightService設置亮度??
  • ????????????????}?finally?{??
  • ????????????????????Trace.traceEnd(Trace.TRACE_TAG_POWER);??
  • ????????????????}??
  • ????????????}??
  • ????????};??
  • ????}??
  • ????return?null;??
  • }??
  • [java]?view plain?copy
  • @Override??
  • public?void?setBrightness(int?brightness)?{??
  • ????setBrightness(brightness,?BRIGHTNESS_MODE_USER);???//亮度模式默認為BRIGHTNESS_MODE_USER??
  • }??
  • ??
  • @Override??
  • public?void?setBrightness(int?brightness,?int?brightnessMode)?{??
  • ????synchronized?(this)?{??
  • ????????int?color?=?brightness?&?0x000000ff;??
  • ????????color?=?0xff000000?|?(color?<<?16)?|?(color?<<?8)?|?color;???//設置光顏色??
  • ????????setLightLocked(color,?LIGHT_FLASH_NONE,?0,?0,?brightnessMode);??
  • ????}??
  • }??
  • private?void?setLightLocked(int?color,?int?mode,?int?onMS,?int?offMS,?int?brightnessMode)?{??
  • ????if?(!LightsUtilsFactory.getInstance().isBatteryOpenWhenNotificationCome(mId,?color)){??
  • ????????if?(!mLocked?&&?(color?!=?mColor?||?mode?!=?mMode?||?onMS?!=?mOnMS?||?offMS?!=?mOffMS?||??
  • ????????????????mBrightnessMode?!=?brightnessMode))?{??
  • ????????????if?(DEBUG?||?isDebugNotifyLight())?Slog.v(TAG,?"setLight?#"?+?mId?+?":?color=#"??
  • ????????????????????+?Integer.toHexString(color)?+?":?brightnessMode="?+?brightnessMode);??
  • ????????????mLastColor?=?mColor;??
  • ????????????mColor?=?color;??
  • ????????????mMode?=?mode;??
  • ????????????mOnMS?=?onMS;??
  • ????????????mOffMS?=?offMS;??
  • ????????????mLastBrightnessMode?=?mBrightnessMode;??
  • ????????????mBrightnessMode?=?brightnessMode;??
  • ????????????Trace.traceBegin(Trace.TRACE_TAG_POWER,?"setLight("?+?mId?+?",?0x"??
  • ????????????????????+?Integer.toHexString(color)?+?")");??
  • ????????????try?{??
  • ????????????????setLight_native(mNativePointer,?mId,?color,?mode,?onMS,?offMS,?brightnessMode);??//調(diào)用jni層設置亮度??
  • ????????????}?finally?{??
  • ????????????????Trace.traceEnd(Trace.TRACE_TAG_POWER);??
  • ????????????}??
  • ????????}??
  • ????}??
  • }??
  • 通過JNI調(diào)用com_android_server_lights_LightsService.cpp的setLight_native函數(shù)
    [java]?view plain?copy
  • static?void?setLight_native(JNIEnv*?/*?env?*/,?jobject?/*?clazz?*/,?jlong?ptr,??
  • ????????jint?light,?jint?colorARGB,?jint?flashMode,?jint?onMS,?jint?offMS,?jint?brightnessMode)??
  • {??
  • ????Devices*?devices?=?(Devices*)ptr;??
  • ????light_state_t?state;??
  • ??
  • ????if?(light?<?0?||?light?>=?LIGHT_COUNT?||?devices->lights[light]?==?NULL)?{??
  • ????????return?;??
  • ????}??
  • ??
  • ????uint32_t?version?=?devices->lights[light]->common.version;??
  • ??
  • ????memset(&state,?0,?sizeof(light_state_t));??
  • ??
  • ????if?(brightnessMode?==?BRIGHTNESS_MODE_LOW_PERSISTENCE)?{??
  • ????????if?(light?!=?LIGHT_INDEX_BACKLIGHT)?{??
  • ????????????ALOGE("Cannot?set?low-persistence?mode?for?non-backlight?device.");??
  • ????????????return;??
  • ????????}??
  • ????????if?(version?<?LIGHTS_DEVICE_API_VERSION_2_0)?{??
  • ????????????//?HAL?impl?has?not?been?upgraded?to?support?this.??
  • ????????????return;??
  • ????????}??
  • ????}?else?{??
  • ????????//?Only?set?non-brightness?settings?when?not?in?low-persistence?mode??
  • ????????state.color?=?colorARGB;??
  • ????????state.flashMode?=?flashMode;??
  • ????????state.flashOnMS?=?onMS;??
  • ????????state.flashOffMS?=?offMS;??
  • ????}??
  • ??
  • ????state.brightnessMode?=?brightnessMode;??
  • ??
  • ????{??
  • ????????ALOGD_IF_SLOW(50,?"Excessive?delay?setting?light");???//當設置亮度耗時大于50ms,就會輸出該行l(wèi)og.??
  • ????????devices->lights[light]->set_light(devices->lights[light],?&state);??
  • ????}??
  • }??
  • 之后調(diào)用BSP向亮度節(jié)點寫入亮度值. 從而點亮屏幕.


    滅屏流程分析

    滅屏總覽


    ? ? ? ? ? ? ? ? ? ?

    在點擊power鍵滅屏過程中,主要流程就是input對按鍵事件的傳輸,傳送到上層處理。在PhoneWindowManager中判斷是否為滅屏事件, 之后就是在power中進行對亮屏狀態(tài)的處理,計算一系列的數(shù)值,并且與AMS,WMS等模塊進行交互,最后調(diào)用底層LCD進行最終的設備狀態(tài)與亮度的設置。滅屏流程與亮屏流程有很多共同流程,在這里只講解滅屏的獨特流程。
    ? ? ? ? ? ? ? ? ? ? ? ? ? ??
    當wakefulness狀態(tài)發(fā)生改變,AMS收到通知。如果亮屏操作,AMS就會通過函數(shù)comeOutOfSleepIfNeedLocked調(diào)用到ActivityStackSupervisor中,將sleep超時消息移除,如果抓的有partial鎖,就將其釋放,最后將在棧頂?shù)腶ctivity顯示出來。
    當亮屏時通過InputManagerService將當前屏幕狀態(tài)傳入JNI中進行記錄,當再次發(fā)生power鍵事件可以方便確認該事件是需要亮屏還是滅屏。
    滅屏時首先在Notifier中通過PhoneWindowManager來通知keyguard系統(tǒng)開始滅屏。
    滅屏動畫
    在PowerManagerService中獲得屏幕的請求狀態(tài)為OFF,即設置state為Display.STATE_OFF,在這里將performScreenOffTransition為true。

    [java]?view plain?copy
  • case?DisplayPowerRequest.POLICY_OFF:??
  • ????state?=?Display.STATE_OFF;??
  • ????performScreenOffTransition?=?true;??
  • ????break;??
  • 調(diào)用animateScreenStateChange進行處理屏幕狀態(tài)。
    [java]?view plain?copy
  • //?Animate?the?screen?state?change?unless?already?animating.??
  • //?The?transition?may?be?deferred,?so?after?this?point?we?will?use?the??
  • //?actual?state?instead?of?the?desired?one.??
  • animateScreenStateChange(state,?performScreenOffTransition);??
  • state?=?mPowerState.getScreenState();??
  • 如果目標亮度不為STATE_ON,STATE_DOZE,STATE_DOZE_SUSPEND屏幕就要去睡眠了。
    [java]?view plain?copy
  • //?Want?screen?off.??
  • mPendingScreenOff?=?true;??
  • if?(mPowerState.getColorFadeLevel()?==?0.0f)?{??
  • ????//?Turn?the?screen?off.??
  • ????//?A?black?surface?is?already?hiding?the?contents?of?the?screen.??
  • ????setScreenState(Display.STATE_OFF);??
  • ????mPendingScreenOff?=?false;??
  • ????mPowerState.dismissColorFadeResources();??
  • }?else?if?(performScreenOffTransition??
  • ????????&&?mPowerState.prepareColorFade(mContext,??
  • ????????????????mColorFadeFadesConfig????
  • ????????????????????????ColorFade.MODE_FADE?:?ColorFade.MODE_COOL_DOWN)??
  • ????????&&?mPowerState.getScreenState()?!=?Display.STATE_OFF)?{??
  • ????//?Perform?the?screen?off?animation.??
  • ????mColorFadeOffAnimator.start();??
  • }?else?{??
  • ????//?Skip?the?screen?off?animation?and?add?a?black?surface?to?hide?the??
  • ????//?contents?of?the?screen.??
  • ????mColorFadeOffAnimator.end();??
  • }??
  • 在這里就要判斷ColorFadeLevel是不是0.0,由于亮屏時將ColorFadeLevel設置為1.0所以走else語句,如果performScreenOffTransition為true并且將ColorFade準備好了就開始滅屏動畫將ColorFadeLevel從1.0漸變?yōu)?.0。但是前面知道將performScreenOffTransition設置為了false,所以就沒有了滅屏動畫,直接將ColorFadeLevel設置為0.0。之后就調(diào)用setScreenState設置狀態(tài)。
    發(fā)送滅屏廣播
    ? ? ? ? ? ? ? ? ? ? ? ? ? ? ??

    power是通過WindowManagerPolicy與PhoneWindowManager進行交互,當屏幕在finishedGoingToSleep時需要通知window進行更新手勢監(jiān)聽,更新方向監(jiān)聽,更新鎖屏超時時間。之后發(fā)送滅屏廣播通知關心滅屏事件的模塊。

    到此為止亮滅屏流程講解完畢.

    版權(quán)聲明:本文為博主原創(chuàng)文章,未經(jīng)博主允許不得轉(zhuǎn)載。 https://blog.csdn.net/fu_kevin0606/article/details/54427641

    總結(jié)

    以上是生活随笔為你收集整理的Android7.0 PowerManagerService亮灭屏分析(三)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。