DisplayManagerService启动及主屏添加-Android13
1、DisplayManagerService启动
1.1 简要时序图
代码位置:frameworks/base/services/core/java/com/android/server/display
frameworks/native/services/displayservice
frameworks/native/services/surfaceflinger
1、多屏幕相关:DisplayDeviceRepository.java、LogicalDisplayMapper.java、LocalDisplayAdapter.java、DisplayEventReceiver.java
屏幕类型 静态屏幕标识符 相关类 本地 local:<stable-id> LocalDisplayAdapter.java 网络 network:<mac-address> WifiDisplayAdapter.java 虚拟 virtual:<package-name-and-name> VirtualDisplayAdapter.java 叠加 overlay:<number> OverlayDisplayAdapter.java,开发者选项中模拟辅助显示设备开启
2、屏幕亮度相关:BrightnessSynchronizer.java
2、DEFAULT_DISPLAY主屏幕添加
AOSP > 文档 > 核心主题 > 显示屏支持
在 Android 11 中, 启动期间报告的第一个屏幕是主屏幕。这与连接类型是内部还是外部并不相关。 不过,主屏幕是不能断开连接的,由此可见,实际操作中的主屏幕必须是内部屏幕。请注意,一些可折叠手机有多个内部屏幕。
辅助屏幕已正确分类为Display.TYPE_INTERNAL
或Display.TYPE_EXTERNAL
(以前分别称为 Display.TYPE_BUILT_IN 和 Display.TYPE_HDMI),具体取决于连接类型。
在 Android 9 及更低版本中,屏幕使用 32 位 ID 表示,其中 0 表示内部屏幕,1 表示外部屏幕,[2, INT32_MAX] 表示 HWC 虚拟屏幕,而 -1 表示无效屏幕或非 HWC 虚拟屏幕。
从 Android 10 开始,屏幕会获得稳定持久的 ID,从而使 SurfaceFlinger 和 DisplayManagerService 可以跟踪两个以上的屏幕并识别以前看到的屏幕。如果 HWC 支持 IComposerClient.getDisplayIdentificationData 并提供屏幕标识数据,SurfaceFlinger 将会解析 EDID 结构并为物理屏幕和 HWC 虚拟屏幕分配稳定的 64 位屏幕 ID。系统会使用选项类型表示 ID,其中 null 值表示无效屏幕或非 HWC 虚拟屏幕。如果 HWC 不支持,SurfaceFlinger 会回退到最多只存在两个物理屏幕的旧版行为。
添加 “内置屏幕”
1080 x 2400
density 420, 420.0 x 420.0 dpi
rotation 0
type INTERNAL
installOrientation 0
09-14 16:10:38.304 607 650 I DisplayDeviceRepository: Display device added: DisplayDeviceInfo{"内置屏幕": uniqueId="local:4619827259835644672", 1080 x 2400, modeId 1, renderFrameRate 60.000004, defaultModeId 1, supportedModes [{id=1, width=1080, height=2400, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], colorMode 0, supportedColorModes [0], hdrCapabilities HdrCapabilities{mSupportedHdrTypes=[], mMaxLuminance=500.0, mMaxAverageLuminance=500.0, mMinLuminance=0.0}, allmSupported false, gameContentTypeSupported false, density 420, 420.0 x 420.0 dpi, appVsyncOff 1000000, presDeadline 16666666, touch INTERNAL, rotation 0, type INTERNAL, address {port=0, model=0x401cec6a7a2b7b}, deviceProductInfo DeviceProductInfo{name=EMU_display_0, manufacturerPnpId=GGL, productId=1, modelYear=null, manufactureDate=ManufactureDate{week=27, year=2006}, connectionToSinkType=0}, state UNKNOWN, committedState UNKNOWN, frameRateOverride , brightnessMinimum 0.0, brightnessMaximum 1.0, brightnessDefault 0.39763778, hdrSdrRatio NaN, FLAG_ALLOWED_TO_BE_DEFAULT_DISPLAY, FLAG_ROTATES_WITH_CONTENT, FLAG_SECURE, FLAG_SUPPORTS_PROTECTED_BUFFERS, FLAG_TRUSTED, installOrientation 0, displayShape DisplayShape{ spec=-1893857183 displayWidth=1080 displayHeight=2400 physicalPixelDisplaySizeRatio=1.0 rotation=0 offsetX=0 offsetY=0 scale=1.0}} 09-14 16:10:38.307 607 650 I LogicalDisplayMapper: Applying layout: [{dispId: 0(ON), displayGroupName: , addr: {port=0, model=0x401cec6a7a2b7b}, mThermalBrightnessThrottlingMapId: null, mRefreshRateZoneId: null, mLeadDisplayId: -1, mThermalRefreshRateThrottlingMapId: null}], Previous layout: null 09-14 16:10:38.317 607 650 I LogicalDisplayMapper: Setting new display group 0 for display 0, from previous group: null 09-14 16:10:38.320 607 650 I LogicalDisplayMapper: Adding new display: 0: DisplayInfo{"内置屏幕", displayId 0, displayGroupId 0, FLAG_SECURE, FLAG_SUPPORTS_PROTECTED_BUFFERS, FLAG_TRUSTED, real 1080 x 2400, largest app 1080 x 2400, smallest app 1080 x 2400, appVsyncOff 1000000, presDeadline 16666666, mode 160.000004, defaultMode 1, modes [{id=1, width=1080, height=2400, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], hdrCapabilities HdrCapabilities{mSupportedHdrTypes=[], mMaxLuminance=500.0, mMaxAverageLuminance=500.0, mMinLuminance=0.0}, userDisabledHdrTypes [], minimalPostProcessingSupported false, rotation 0, state UNKNOWN, committedState UNKNOWN, type INTERNAL, uniqueId "local:4619827259835644672", app 1080 x 2400, density 420 (420.0 x 420.0) dpi, layerStack 0, colorMode 0, supportedColorModes [0], address {port=0, model=0x401cec6a7a2b7b}, deviceProductInfo DeviceProductInfo{name=EMU_display_0, manufacturerPnpId=GGL, productId=1, modelYear=null, manufactureDate=ManufactureDate{week=27, year=2006}, connectionToSinkType=0}, removeMode 0, refreshRateOverride 0.0, brightnessMinimum 0.0, brightnessMaximum 1.0, brightnessDefault 0.39763778, installOrientation ROTATION_0, layoutLimitedRefreshRate null, hdrSdrRatio not_available, thermalRefreshRateThrottling {}, thermalBrightnessThrottlingDataId default} 09-14 16:10:49.174 607 650 I DisplayDeviceRepository: Display device changed state: "内置屏幕", ON 09-14 16:10:49.185 607 650 I DisplayDeviceRepository: Display device changed state: "内置屏幕", ON 09-14 16:10:50.814 607 650 I DisplayDeviceRepository: Display device added: DisplayDeviceInfo{"叠加视图 #1": uniqueId="overlay:1", 1920 x 1080, modeId 2, renderFrameRate 60.000004, defaultModeId 2, supportedModes [{id=2, width=1920, height=1080, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], colorMode 0, supportedColorModes [0], hdrCapabilities null, allmSupported false, gameContentTypeSupported false, density 320, 320.0 x 320.0 dpi, appVsyncOff 0, presDeadline 33333332, touch VIRTUAL, rotation 0, type OVERLAY, deviceProductInfo null, state ON, committedState UNKNOWN, frameRateOverride , brightnessMinimum 0.0, brightnessMaximum 0.0, brightnessDefault 0.0, hdrSdrRatio NaN, FLAG_SECURE, FLAG_PRESENTATION, FLAG_TRUSTED, installOrientation 0, displayShape DisplayShape{ spec=729782573 displayWidth=1920 displayHeight=1080 physicalPixelDisplaySizeRatio=1.0 rotation=0 offsetX=0 offsetY=0 scale=1.0}} 09-14 16:10:50.820 607 650 I LogicalDisplayMapper: Applying layout: [{dispId: 0(ON), displayGroupName: , addr: {port=0, model=0x401cec6a7a2b7b}, mThermalBrightnessThrottlingMapId: null, mRefreshRateZoneId: null, mLeadDisplayId: -1, mThermalRefreshRateThrottlingMapId: null}], Previous layout: [{dispId: 0(ON), displayGroupName: , addr: {port=0, model=0x401cec6a7a2b7b}, mThermalBrightnessThrottlingMapId: null, mRefreshRateZoneId: null, mLeadDisplayId: -1, mThermalRefreshRateThrottlingMapId: null}] 09-14 16:10:50.821 607 650 I LogicalDisplayMapper: Setting new display group 0 for display 2, from previous group: null 09-14 16:10:50.825 607 650 I LogicalDisplayMapper: Adding new display: 2: DisplayInfo{"叠加视图 #1", displayId 2, displayGroupId 0, FLAG_SECURE, FLAG_PRESENTATION, FLAG_TRUSTED, real 1920 x 1080, largest app 1920 x 1080, smallest app 1920 x 1080, appVsyncOff 0, presDeadline 33333332, mode 260.000004, defaultMode 2, modes [{id=2, width=1920, height=1080, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], hdrCapabilities null, userDisabledHdrTypes [], minimalPostProcessingSupported false, rotation 0, state ON, committedState UNKNOWN, type OVERLAY, uniqueId "overlay:1", app 1920 x 1080, density 320 (320.0 x 320.0) dpi, layerStack 2, colorMode 0, supportedColorModes [0], deviceProductInfo null, removeMode 0, refreshRateOverride 0.0, brightnessMinimum 0.0, brightnessMaximum 0.0, brightnessDefault 0.0, installOrientation ROTATION_0, layoutLimitedRefreshRate null, hdrSdrRatio not_available, thermalRefreshRateThrottling {}, thermalBrightnessThrottlingDataId default} 09-14 16:10:58.994 607 650 I DisplayDeviceRepository: Display device changed: DisplayDeviceInfo{"内置屏幕": uniqueId="local:4619827259835644672", 1080 x 2400, modeId 1, renderFrameRate 60.000004, defaultModeId 1, supportedModes [{id=1, width=1080, height=2400, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], colorMode 0, supportedColorModes [0], hdrCapabilities HdrCapabilities{mSupportedHdrTypes=[], mMaxLuminance=500.0, mMaxAverageLuminance=500.0, mMinLuminance=0.0}, allmSupported false, gameContentTypeSupported false, density 420, 420.0 x 420.0 dpi, appVsyncOff 1000000, presDeadline 16666666, cutout DisplayCutout{insets=Rect(0, 132 - 0, 0) waterfall=Insets{left=0, top=0, right=0, bottom=0} boundingRect={Bounds=[Rect(0, 0 - 0, 0), Rect(479, 0 - 601, 132), Rect(0, 0 - 0, 0), Rect(0, 0 - 0, 0)]} cutoutPathParserInfo={CutoutPathParserInfo{displayWidth=1080 displayHeight=2400 physicalDisplayWidth=1080 physicalDisplayHeight=2400 density={2.625} cutoutSpec={m 576,65.75 a 36.25,36.25 0 0 0 -72.5,0 36.25,36.25 0 0 0 72.5,0 z @left} rotation={0} scale={1.0} physicalPixelDisplaySizeRatio={1.0}}}}, touch INTERNAL, rotation 0, type INTERNAL, address {port=0, model=0x401cec6a7a2b7b}, deviceProductInfo DeviceProductInfo{name=EMU_display_0, manufacturerPnpId=GGL, productId=1, modelYear=null, manufactureDate=ManufactureDate{week=27, year=2006}, connectionToSinkType=0}, state ON, committedState ON, frameRateOverride , brightnessMinimum 0.0, brightnessMaximum 1.0, brightnessDefault 0.39763778, hdrSdrRatio NaN, roundedCorners RoundedCorners{[RoundedCorner{position=TopLeft, radius=104, center=Point(104, 104)}, RoundedCorner{position=TopRight, radius=104, center=Point(976, 104)}, RoundedCorner{position=BottomRight, radius=102, center=Point(978, 2298)}, RoundedCorner{position=BottomLeft, radius=102, center=Point(102, 2298)}]}, FLAG_ALLOWED_TO_BE_DEFAULT_DISPLAY, FLAG_ROTATES_WITH_CONTENT, FLAG_SECURE, FLAG_SUPPORTS_PROTECTED_BUFFERS, FLAG_TRUSTED, installOrientation 0, displayShape DisplayS ... 09-14 16:10:59.203 607 650 I DisplayDeviceRepository: Display device changed: DisplayDeviceInfo{"叠加视图 #1": uniqueId="overlay:1", 1920 x 1080, modeId 2, renderFrameRate 60.000004, defaultModeId 2, supportedModes [{id=2, width=1920, height=1080, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], colorMode 0, supportedColorModes [0], hdrCapabilities null, allmSupported false, gameContentTypeSupported false, density 320, 320.0 x 320.0 dpi, appVsyncOff 0, presDeadline 33333332, touch VIRTUAL, rotation 0, type OVERLAY, deviceProductInfo null, state ON, committedState UNKNOWN, frameRateOverride , brightnessMinimum 0.0, brightnessMaximum 0.0, brightnessDefault 0.0, hdrSdrRatio NaN, FLAG_SECURE, FLAG_PRESENTATION, FLAG_TRUSTED, installOrientation 0, displayShape DisplayShape{ spec=729782573 displayWidth=1920 displayHeight=1080 physicalPixelDisplaySizeRatio=1.0 rotation=0 offsetX=0 offsetY=0 scale=1.0}} 09-14 16:10:59.210 607 650 I DisplayDeviceRepository: Display device changed: DisplayDeviceInfo{"叠加视图 #1": uniqueId="overlay:1", 1920 x 1080, modeId 2, renderFrameRate 60.000004, defaultModeId 2, supportedModes [{id=2, width=1920, height=1080, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], colorMode 0, supportedColorModes [0], hdrCapabilities null, allmSupported false, gameContentTypeSupported false, density 320, 320.0 x 320.0 dpi, appVsyncOff 0, presDeadline 33333332, touch VIRTUAL, rotation 0, type OVERLAY, deviceProductInfo null, state ON, committedState UNKNOWN, frameRateOverride , brightnessMinimum 0.0, brightnessMaximum 0.0, brightnessDefault 0.0, hdrSdrRatio NaN, FLAG_SECURE, FLAG_PRESENTATION, FLAG_TRUSTED, installOrientation 0, displayShape DisplayShape{ spec=729782573 displayWidth=1920 displayHeight=1080 physicalPixelDisplaySizeRatio=1.0 rotation=0 offsetX=0 offsetY=0 scale=1.0}} 09-14 16:10:44.078 607 650 I DisplayDeviceRepository: Display device changed: DisplayDeviceInfo{"叠加视图 #1": uniqueId="overlay:1", 1920 x 1080, modeId 2, renderFrameRate 60.000004, defaultModeId 2, supportedModes [{id=2, width=1920, height=1080, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], colorMode 0, supportedColorModes [0], hdrCapabilities null, allmSupported false, gameContentTypeSupported false, density 320, 320.0 x 320.0 dpi, appVsyncOff 0, presDeadline 33333332, touch VIRTUAL, rotation 0, type OVERLAY, deviceProductInfo null, state ON, committedState UNKNOWN, frameRateOverride , brightnessMinimum 0.0, brightnessMaximum 0.0, brightnessDefault 0.0, hdrSdrRatio NaN, FLAG_SECURE, FLAG_PRESENTATION, FLAG_TRUSTED, installOrientation 0, displayShape DisplayShape{ spec=729782573 displayWidth=1920 displayHeight=1080 physicalPixelDisplaySizeRatio=1.0 rotation=0 offsetX=0 offsetY=0 scale=1.0}} 09-14 16:10:44.343 607 650 I LogicalDisplayMapper: Requesting Transition to state: 0, from state=-1, interactive=true, mBootCompleted=true 09-14 16:10:44.343 607 650 I LogicalDisplayMapper: Applying layout: [{dispId: 0(ON), displayGroupName: , addr: {port=0, model=0x401cec6a7a2b7b}, mThermalBrightnessThrottlingMapId: null, mRefreshRateZoneId: null, mLeadDisplayId: -1, mThermalRefreshRateThrottlingMapId: null}], Previous layout: [{dispId: 0(ON), displayGroupName: , addr: {port=0, model=0x401cec6a7a2b7b}, mThermalBrightnessThrottlingMapId: null, mRefreshRateZoneId: null, mLeadDisplayId: -1, mThermalRefreshRateThrottlingMapId: null}] 09-14 16:10:48.835 607 650 I DisplayDeviceRepository: Display device changed: DisplayDeviceInfo{"内置屏幕": uniqueId="local:4619827259835644672", 1080 x 2400, modeId 1, renderFrameRate 60.000004, defaultModeId 1, supportedModes [{id=1, width=1080, height=2400, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], colorMode 0, supportedColorModes [0], hdrCapabilities HdrCapabilities{mSupportedHdrTypes=[], mMaxLuminance=500.0, mMaxAverageLuminance=500.0, mMinLuminance=0.0}, allmSupported false, gameContentTypeSupported false, density 420, 420.0 x 420.0 dpi, appVsyncOff 1000000, presDeadline 16666666, cutout DisplayCutout{insets=Rect(0, 132 - 0, 0) waterfall=Insets{left=0, top=0, right=0, bottom=0} boundingRect={Bounds=[Rect(0, 0 - 0, 0), Rect(479, 0 - 601, 132), Rect(0, 0 - 0, 0), Rect(0, 0 - 0, 0)]} cutoutPathParserInfo={CutoutPathParserInfo{displayWidth=1080 displayHeight=2400 physicalDisplayWidth=1080 physicalDisplayHeight=2400 density={2.625} cutoutSpec={m 576,65.75 a 36.25,36.25 0 0 0 -72.5,0 36.25,36.25 0 0 0 72.5,0 z @left} rotation={0} scale={1.0} physicalPixelDisplaySizeRatio={1.0}}}}, touch INTERNAL, rotation 0, type INTERNAL, address {port=0, model=0x401cec6a7a2b7b}, deviceProductInfo DeviceProductInfo{name=EMU_display_0, manufacturerPnpId=GGL, productId=1, modelYear=null, manufactureDate=ManufactureDate{week=27, year=2006}, connectionToSinkType=0}, state ON, committedState ON, frameRateOverride , brightnessMinimum 0.0, brightnessMaximum 1.0, brightnessDefault 0.39763778, hdrSdrRatio NaN, roundedCorners RoundedCorners{[RoundedCorner{position=TopLeft, radius=104, center=Point(104, 104)}, RoundedCorner{position=TopRight, radius=104, center=Point(976, 104)}, RoundedCorner{position=BottomRight, radius=102, center=Point(978, 2298)}, RoundedCorner{position=BottomLeft, radius=102, center=Point(102, 2298)}]}, FLAG_ALLOWED_TO_BE_DEFAULT_DISPLAY, FLAG_ROTATES_WITH_CONTENT, FLAG_SECURE, FLAG_SUPPORTS_PROTECTED_BUFFERS, FLAG_TRUSTED, installOrientation 0, displayShape DisplayS ... 09-14 16:11:13.939 607 650 I DisplayDeviceRepository: Display device changed: DisplayDeviceInfo{"叠加视图 #1": uniqueId="overlay:1", 1920 x 1080, modeId 2, renderFrameRate 60.000004, defaultModeId 2, supportedModes [{id=2, width=1920, height=1080, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], colorMode 0, supportedColorModes [0], hdrCapabilities null, allmSupported false, gameContentTypeSupported false, density 320, 320.0 x 320.0 dpi, appVsyncOff 0, presDeadline 33333332, touch VIRTUAL, rotation 0, type OVERLAY, deviceProductInfo null, state ON, committedState UNKNOWN, frameRateOverride , brightnessMinimum 0.0, brightnessMaximum 0.0, brightnessDefault 0.0, hdrSdrRatio NaN, FLAG_SECURE, FLAG_PRESENTATION, FLAG_TRUSTED, installOrientation 0, displayShape DisplayShape{ spec=729782573 displayWidth=1920 displayHeight=1080 physicalPixelDisplaySizeRatio=1.0 rotation=0 offsetX=0 offsetY=0 scale=1.0}} 09-14 16:11:24.379 607 650 I DisplayDeviceRepository: Display device changed state: "内置屏幕", OFF 09-14 16:11:24.390 607 650 I DisplayDeviceRepository: Display device changed state: "内置屏幕", OFF 09-14 16:11:24.425 607 650 I DisplayDeviceRepository: Display device changed state: "叠加视图 #1", OFF 09-14 16:11:24.478 607 650 I DisplayDeviceRepository: Display device changed: DisplayDeviceInfo{"叠加视图 #1": uniqueId="overlay:1", 1920 x 1080, modeId 2, renderFrameRate 60.000004, defaultModeId 2, supportedModes [{id=2, width=1920, height=1080, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], colorMode 0, supportedColorModes [0], hdrCapabilities null, allmSupported false, gameContentTypeSupported false, density 320, 320.0 x 320.0 dpi, appVsyncOff 0, presDeadline 33333332, touch VIRTUAL, rotation 0, type OVERLAY, deviceProductInfo null, state OFF, committedState UNKNOWN, frameRateOverride , brightnessMinimum 0.0, brightnessMaximum 0.0, brightnessDefault 0.0, hdrSdrRatio NaN, FLAG_SECURE, FLAG_PRESENTATION, FLAG_TRUSTED, installOrientation 0, displayShape DisplayShape{ spec=729782573 displayWidth=1920 displayHeight=1080 physicalPixelDisplaySizeRatio=1.0 rotation=0 offsetX=0 offsetY=0 scale=1.0}} 09-14 16:11:27.676 607 650 I DisplayDeviceRepository: Display device changed state: "内置屏幕", ON 09-14 16:11:27.688 607 650 I DisplayDeviceRepository: Display device changed state: "内置屏幕", ON 09-14 16:11:27.777 607 650 I DisplayDeviceRepository: Display device changed state: "叠加视图 #1", ON 09-14 16:11:27.829 607 650 I DisplayDeviceRepository: Display device changed: DisplayDeviceInfo{"叠加视图 #1": uniqueId="overlay:1", 1920 x 1080, modeId 2, renderFrameRate 60.000004, defaultModeId 2, supportedModes [{id=2, width=1920, height=1080, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], colorMode 0, supportedColorModes [0], hdrCapabilities null, allmSupported false, gameContentTypeSupported false, density 320, 320.0 x 320.0 dpi, appVsyncOff 0, presDeadline 33333332, touch VIRTUAL, rotation 0, type OVERLAY, deviceProductInfo null, state ON, committedState UNKNOWN, frameRateOverride , brightnessMinimum 0.0, brightnessMaximum 0.0, brightnessDefault 0.0, hdrSdrRatio NaN, FLAG_SECURE, FLAG_PRESENTATION, FLAG_TRUSTED, installOrientation 0, displayShape DisplayShape{ spec=729782573 displayWidth=1920 displayHeight=1080 physicalPixelDisplaySizeRatio=1.0 rotation=0 offsetX=0 offsetY=0 scale=1.0}} 09-14 16:14:42.174 607 650 I DisplayDeviceRepository: Display device removed: DisplayDeviceInfo{"叠加视图 #1": uniqueId="overlay:1", 1920 x 1080, modeId 2, renderFrameRate 60.000004, defaultModeId 2, supportedModes [{id=2, width=1920, height=1080, fps=60.000004, alternativeRefreshRates=[], supportedHdrTypes=[]}], colorMode 0, supportedColorModes [0], hdrCapabilities null, allmSupported false, gameContentTypeSupported false, density 320, 320.0 x 320.0 dpi, appVsyncOff 0, presDeadline 33333332, touch VIRTUAL, rotation 0, type OVERLAY, deviceProductInfo null, state ON, committedState UNKNOWN, frameRateOverride , brightnessMinimum 0.0, brightnessMaximum 0.0, brightnessDefault 0.0, hdrSdrRatio NaN, FLAG_SECURE, FLAG_PRESENTATION, FLAG_TRUSTED, installOrientation 0, displayShape DisplayShape{ spec=729782573 displayWidth=1920 displayHeight=1080 physicalPixelDisplaySizeRatio=1.0 rotation=0 offsetX=0 offsetY=0 scale=1.0}} 09-14 16:14:42.191 607 650 I LogicalDisplayMapper: Removing display: 2
2.1 物理屏热插拔监听
1、启动注册 LocalDisplayAdapter.registerLocked 时查看添加
tryConnectDisplayLocked(physicalDisplayId)
2、DisplayEventReceiver
监听添加屏幕tryConnectDisplayLocked(physicalDisplayId)
:
- DisplayEventListener监听注册流程
LocalDisplayAdapter.java#mInjector.setDisplayEventListenerLocked(getHandler().getLooper(), new LocalDisplayEventListener()) > DisplayEventReceiver.java#nativeInit > android_view_DisplayEventReceiver.cpp::nativeInit > DisplayEventDispatcher.cpp::mReceiver > DisplayEventReceiver.cpp::mEventConnection > SurfaceFlinger.cpp::createDisplayEventConnection > Scheduler.cpp::createDisplayEventConnection > EventThread.cpp::createEventConnection > new EventThreadConnection
- DisplayEventReceiver监听接受流程
HWC::onHotplug > SurfaceFlinger.cpp::dispatchDisplayHotplugEvent > Scheduler.cpp::onHotplugReceived > EventThread.cpp::onHotplugReceived > EventThread::threadMain > EventThread::dispatchEvent > EventThreadConnection::postEvent > DisplayEventReceiver.cpp::sendEvents > gui::BitTube::sendObjects(dataChannel, events, count) > ==LooperCallback== DisplayEventDispatcher.cpp::handleEvent > DisplayEventDispatcher::processPendingEvents > android_view_DisplayEventReceiver.cpp::NativeDisplayEventReceiver::dispatchHotplug > LocalDisplayAdapter.java#ProxyDisplayEventReceiver#onHotplug > LocalDisplayEventListener#onHotplug > LocalDisplayAdapter.java#tryConnectDisplayLocked
frameworks/base/services/core/java/com/android/server/display/LocalDisplayAdapter.java
private void tryConnectDisplayLocked(long physicalDisplayId) {
final IBinder displayToken =
mSurfaceControlProxy.getPhysicalDisplayToken(physicalDisplayId);
if (displayToken != null) {
SurfaceControl.StaticDisplayInfo staticInfo =
mSurfaceControlProxy.getStaticDisplayInfo(displayToken);
if (staticInfo == null) {
Slog.w(TAG, "No valid static info found for display device " + physicalDisplayId);
return;
}
SurfaceControl.DynamicDisplayInfo dynamicInfo =
mSurfaceControlProxy.getDynamicDisplayInfo(displayToken);
if (dynamicInfo == null) {
Slog.w(TAG, "No valid dynamic info found for display device " + physicalDisplayId);
return;
}
if (dynamicInfo.supportedDisplayModes == null) {
// There are no valid modes for this device, so we can't use it
Slog.w(TAG, "No valid modes found for display device " + physicalDisplayId);
return;
}
if (dynamicInfo.activeDisplayModeId < 0) {
// There is no active mode, and for now we don't have the
// policy to set one.
Slog.w(TAG, "No valid active mode found for display device " + physicalDisplayId);
return;
}
if (dynamicInfo.activeColorMode < 0) {
// We failed to get the active color mode. We don't bail out here since on the next
// configuration pass we'll go ahead and set it to whatever it was set to last (or
// COLOR_MODE_NATIVE if this is the first configuration).
Slog.w(TAG, "No valid active color mode for display device " + physicalDisplayId);
dynamicInfo.activeColorMode = Display.COLOR_MODE_INVALID;
}
SurfaceControl.DesiredDisplayModeSpecs modeSpecs =
mSurfaceControlProxy.getDesiredDisplayModeSpecs(displayToken);
LocalDisplayDevice device = mDevices.get(physicalDisplayId);
if (device == null) {
// Display was added.
final boolean isFirstDisplay = mDevices.size() == 0;
device = new LocalDisplayDevice(displayToken, physicalDisplayId, staticInfo,
dynamicInfo, modeSpecs, isFirstDisplay);
mDevices.put(physicalDisplayId, device);
sendDisplayDeviceEventLocked(device, DISPLAY_DEVICE_EVENT_ADDED);
} else if (device.updateDisplayPropertiesLocked(staticInfo, dynamicInfo,
modeSpecs)) {
sendDisplayDeviceEventLocked(device, DISPLAY_DEVICE_EVENT_CHANGED);
}
} else {
// The display is no longer available. Ignore the attempt to add it.
// If it was connected but has already been disconnected, we'll get a
// disconnect event that will remove it from mDevices.
}
}
2.2 物理屏信息
硬件插入显示器
HWC::onHotplug
,依赖于Hardware Composer API
。设备制造商必须实现IComposerClient 2.3
HIDL 接口 (android.hardware.graphics.composer@2.3::IComposerClient
) 的getDisplayIdentificationData
方法,或者针对较旧的libhardware
实现情况实现相应的hardware/hwcomposer2.h
函数
sf
创建DisplayDevice:SurfaceFlinger::setupNewDisplayDeviceInternal
DMS
创建DisplayDevice、DisplayDeviceInfo:tryConnectDisplayLocked
、getDisplayDeviceInfoLocked()
frameworks/base/services/core/java/com/android/server/display/DisplayDevice.java
frameworks/base/services/core/java/com/android/server/display/DisplayDeviceInfo.java
frameworks/base/services/core/java/com/android/server/display/LogicalDisplay.java
frameworks/base/core/java/android/view/DisplayInfo.java
DisplayDevice.java | DisplayDeviceInfo.java |
---|---|
IBinder mDisplayToken | String name |
String mUniqueId | String uniqueId |
DisplayDeviceConfig mDisplayDeviceConfig | int width |
int mCurrentLayerStack = -1 | int height |
int mCurrentFlags = 0 | int modeId |
int mCurrentOrientation = -1 | int defaultModeId |
Rect mCurrentLayerStackRect | Display.Mode[] supportedModes = Display.Mode.EMPTY_ARRAY |
Rect mCurrentDisplayRect | int colorMode |
Context mContext | int[] supportedColorModes = { Display.COLOR_MODE_DEFAULT } |
Surface mCurrentSurface | Display.HdrCapabilities hdrCapabilities |
DisplayDeviceInfo mDebugLastLoggedDeviceInfo | boolean allmSupported |
boolean gameContentTypeSupported | |
int densityDpi | |
float xDpi | |
float yDpi | |
long appVsyncOffsetNanos | |
long presentationDeadlineNanos | |
int flags | |
DisplayCutout displayCutout | |
RoundedCorners roundedCorners | |
int touch | |
int rotation = Surface.ROTATION_0 | |
int type | |
DisplayAddress address | |
DeviceProductInfo deviceProductInfo | |
int state = Display.STATE_ON | |
int ownerUid | |
String ownerPackageName | |
DisplayEventReceiver.FrameRateOverride[] frameRateOverrides = new DisplayEventReceiver.FrameRateOverride[0] | |
float brightnessMinimum | |
float brightnessMaximum | |
float brightnessDefault | |
int installOrientation = Surface.ROTATION_0 |
frameworks/native/libs/ui/include/ui/DisplayIdentification.h
frameworks/native/libs/ui/include/ui/DisplayId.h
frameworks/native/services/surfaceflinger/DisplayDevice.h
frameworks/native/services/surfaceflinger/CompositionEngine/include/compositionengine/DisplayCreationArgs.h
frameworks/native/libs/ui/include/ui/StaticDisplayInfo.h
frameworks/native/libs/ui/include/ui/DynamicDisplayInfo.h
DisplayIdentificationInfo | DisplayDeviceState | DisplayCreationArgs | DisplayDevice | StaticDisplayInfo | DynamicDisplayInfo |
---|---|---|---|---|---|
PhysicalDisplayId id | struct Physical | DisplayId id | constexpr static float sDefaultMinLumiance = 0.0 | DisplayConnectionType connectionType = DisplayConnectionType::Internal | std::vector<ui::DisplayMode> supportedDisplayModes |
std::string name | int32_t sequenceId = sNextSequenceId++ | ui::Size pixels = ui::kInvalidSize | constexpr static float sDefaultMaxLumiance = 500.0 | float density = 0.f | ui::DisplayModeId activeDisplayModeId |
std::optional<DeviceProductInfo> deviceProductInfo | std::optional<Physical> physical | bool isSecure = false | const sp<SurfaceFlinger> mFlinger | bool secure = false | std::vector<ui::ColorMode> supportedColorModes |
sp<IGraphicBufferProducer> surface | Hwc2::PowerAdvisor* powerAdvisor = nullptr | HWComposer& mHwComposer | std::optional<DeviceProductInfo> deviceProductInfo | ||
ui::LayerStack layerStack | std::string name | const wp<IBinder> mDisplayToken | Rotation installOrientation = ROTATION_0 | ui::ColorMode activeColorMode | |
uint32_t flags = 0 | const int32_t mSequenceId | HdrCapabilities hdrCapabilities | |||
Rect layerStackSpaceRect | const std::optional<ui::DisplayConnectionType> mConnectionType | bool autoLowLatencyModeSupported | |||
Rect orientedDisplaySpaceRect | const std::shared_ptr<compositionengine::Display> mCompositionDisplay | bool gameContentTypeSupported | |||
ui::Rotation orientation = ui::ROTATION_0 | std::string mDisplayName | ui::DisplayModeId preferredBootDisplayMode | |||
uint32_t width = 0 | std::string mActiveModeFPSTrace | std::optional<ui::DisplayMode> getActiveDisplayMode() const | |||
uint32_t height = 0 | std::string mActiveModeFPSHwcTrace | ||||
std::string displayName | const ui::Rotation mPhysicalOrientation | ||||
bool isSecure = false | ui::Rotation mOrientation = ui::ROTATION_0 | ||||
static std::atomic<int32_t> sNextSequenceId | static ui::Transform::RotationFlags sPrimaryDisplayRotationFlags | ||||
hardware::graphics::composer::hal::PowerMode mPowerMode = hardware::graphics::composer::hal::PowerMode::OFF | |||||
DisplayModePtr mActiveMode | |||||
std::optional<float> mStagedBrightness = std::nullopt | |||||
float mBrightness = -1.f | |||||
const DisplayModes mSupportedModes | |||||
std::atomic<nsecs_t> mLastHwVsync = 0 | |||||
const bool mIsPrimary | |||||
uint32_t mFlags = 0 | |||||
std::optional<DeviceProductInfo> mDeviceProductInfo | |||||
std::vector<ui::Hdr> mOverrideHdrTypes | |||||
std::shared_ptr<scheduler::RefreshRateConfigs> mRefreshRateConfigs | |||||
std::unique_ptr<RefreshRateOverlay> mRefreshRateOverlay | |||||
mutable std::mutex mActiveModeLock | |||||
ActiveModeInfo mDesiredActiveMode GUARDED_BY(mActiveModeLock) | |||||
TracedOrdinal<bool> mDesiredActiveModeChanged GUARDED_BY(mActiveModeLock) = {“DesiredActiveModeChanged”, false} | |||||
ActiveModeInfo mUpcomingActiveMode GUARDED_BY(kMainThreadContext) |
3、默认屏幕亮度
frameworks/base/core/java/com/android/internal/display/BrightnessSynchronizer.java
public void startSynchronizing() {
if (mDisplayManager == null) {
mDisplayManager = mContext.getSystemService(DisplayManager.class);
}
if (mBrightnessSyncObserver.isObserving()) {
Slog.wtf(TAG, "Brightness sync observer requesting synchronization a second time.");
return;
}
mLatestFloatBrightness = getScreenBrightnessFloat();
mLatestIntBrightness = getScreenBrightnessInt();
Slog.i(TAG, "Initial brightness readings: " + mLatestIntBrightness + "(int), "
+ mLatestFloatBrightness + "(float)");
if (!Float.isNaN(mLatestFloatBrightness)) {
mPendingUpdate = new BrightnessUpdate(BrightnessUpdate.TYPE_FLOAT,
mLatestFloatBrightness);
} else if (mLatestIntBrightness != PowerManager.BRIGHTNESS_INVALID) {
mPendingUpdate = new BrightnessUpdate(BrightnessUpdate.TYPE_INT,
mLatestIntBrightness);
} else {
final float defaultBrightness = mContext.getResources().getFloat(
com.android.internal.R.dimen.config_screenBrightnessSettingDefaultFloat);
mPendingUpdate = new BrightnessUpdate(BrightnessUpdate.TYPE_FLOAT, defaultBrightness);
Slog.i(TAG, "Setting initial brightness to default value of: " + defaultBrightness);
}
mBrightnessSyncObserver.startObserving();
mHandler.sendEmptyMessageAtTime(MSG_RUN_UPDATE, mClock.uptimeMillis());
}