diff options
12 files changed, 292 insertions, 111 deletions
diff --git a/services/core/java/com/android/server/display/config/RefreshRateData.java b/services/core/java/com/android/server/display/config/RefreshRateData.java index b186fd57e31f..d7ed904e398d 100644 --- a/services/core/java/com/android/server/display/config/RefreshRateData.java +++ b/services/core/java/com/android/server/display/config/RefreshRateData.java @@ -20,6 +20,10 @@ import android.annotation.Nullable; import android.content.res.Resources; import com.android.internal.R; +import com.android.internal.annotations.VisibleForTesting; + +import java.util.Collections; +import java.util.List; /** * RefreshRates config for display @@ -58,12 +62,17 @@ public class RefreshRateData { */ public final int defaultRefreshRateInHbmSunlight; + public final List<SupportedModeData> lowPowerSupportedModes; + + @VisibleForTesting public RefreshRateData(int defaultRefreshRate, int defaultPeakRefreshRate, - int defaultRefreshRateInHbmHdr, int defaultRefreshRateInHbmSunlight) { + int defaultRefreshRateInHbmHdr, int defaultRefreshRateInHbmSunlight, + List<SupportedModeData> lowPowerSupportedModes) { this.defaultRefreshRate = defaultRefreshRate; this.defaultPeakRefreshRate = defaultPeakRefreshRate; this.defaultRefreshRateInHbmHdr = defaultRefreshRateInHbmHdr; this.defaultRefreshRateInHbmSunlight = defaultRefreshRateInHbmSunlight; + this.lowPowerSupportedModes = Collections.unmodifiableList(lowPowerSupportedModes); } @@ -71,9 +80,10 @@ public class RefreshRateData { public String toString() { return "RefreshRateData {" + "defaultRefreshRate: " + defaultRefreshRate - + "defaultPeakRefreshRate: " + defaultPeakRefreshRate - + "defaultRefreshRateInHbmHdr: " + defaultRefreshRateInHbmHdr - + "defaultRefreshRateInHbmSunlight: " + defaultRefreshRateInHbmSunlight + + ", defaultPeakRefreshRate: " + defaultPeakRefreshRate + + ", defaultRefreshRateInHbmHdr: " + defaultRefreshRateInHbmHdr + + ", defaultRefreshRateInHbmSunlight: " + defaultRefreshRateInHbmSunlight + + ", lowPowerSupportedModes=" + lowPowerSupportedModes + "} "; } @@ -90,8 +100,13 @@ public class RefreshRateData { int defaultRefreshRateInHbmSunlight = loadDefaultRefreshRateInHbmSunlight( refreshRateConfigs, resources); + NonNegativeFloatToFloatMap modes = + refreshRateConfigs == null ? null : refreshRateConfigs.getLowPowerSupportedModes(); + List<SupportedModeData> lowPowerSupportedModes = SupportedModeData.load(modes); + return new RefreshRateData(defaultRefreshRate, defaultPeakRefreshRate, - defaultRefreshRateInHbmHdr, defaultRefreshRateInHbmSunlight); + defaultRefreshRateInHbmHdr, defaultRefreshRateInHbmSunlight, + lowPowerSupportedModes); } private static int loadDefaultRefreshRate( diff --git a/services/core/java/com/android/server/display/config/SensorData.java b/services/core/java/com/android/server/display/config/SensorData.java index 6ad13c3b8a40..8bfc4a3ad77a 100644 --- a/services/core/java/com/android/server/display/config/SensorData.java +++ b/services/core/java/com/android/server/display/config/SensorData.java @@ -24,7 +24,6 @@ import android.text.TextUtils; import com.android.internal.annotations.VisibleForTesting; import com.android.server.display.feature.DisplayManagerFlags; -import java.util.ArrayList; import java.util.Collections; import java.util.List; @@ -42,7 +41,7 @@ public class SensorData { public final String name; public final float minRefreshRate; public final float maxRefreshRate; - public final List<SupportedMode> supportedModes; + public final List<SupportedModeData> supportedModes; @VisibleForTesting public SensorData() { @@ -61,7 +60,7 @@ public class SensorData { @VisibleForTesting public SensorData(String type, String name, float minRefreshRate, float maxRefreshRate, - List<SupportedMode> supportedModes) { + List<SupportedModeData> supportedModes) { this.type = type; this.name = name; this.minRefreshRate = minRefreshRate; @@ -214,26 +213,11 @@ public class SensorData { minRefreshRate = rr.getMinimum().floatValue(); maxRefreshRate = rr.getMaximum().floatValue(); } - ArrayList<SupportedMode> supportedModes = new ArrayList<>(); - NonNegativeFloatToFloatMap configSupportedModes = sensorDetails.getSupportedModes(); - if (configSupportedModes != null) { - for (NonNegativeFloatToFloatPoint supportedMode : configSupportedModes.getPoint()) { - supportedModes.add(new SupportedMode(supportedMode.getFirst().floatValue(), - supportedMode.getSecond().floatValue())); - } - } + List<SupportedModeData> supportedModes = SupportedModeData.load( + sensorDetails.getSupportedModes()); return new SensorData(sensorDetails.getType(), sensorDetails.getName(), minRefreshRate, maxRefreshRate, supportedModes); } - public static class SupportedMode { - public final float refreshRate; - public final float vsyncRate; - - public SupportedMode(float refreshRate, float vsyncRate) { - this.refreshRate = refreshRate; - this.vsyncRate = vsyncRate; - } - } } diff --git a/services/core/java/com/android/server/display/config/SupportedModeData.java b/services/core/java/com/android/server/display/config/SupportedModeData.java new file mode 100644 index 000000000000..3c82884e1024 --- /dev/null +++ b/services/core/java/com/android/server/display/config/SupportedModeData.java @@ -0,0 +1,54 @@ +/* + * Copyright (C) 2024 The Android Open Source Project + * + * 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.server.display.config; + +import android.annotation.Nullable; + +import java.util.ArrayList; +import java.util.List; + +/** + * Supported display mode data. Display mode is uniquely identified by refreshRate-vsync pair + */ +public class SupportedModeData { + public final float refreshRate; + public final float vsyncRate; + + public SupportedModeData(float refreshRate, float vsyncRate) { + this.refreshRate = refreshRate; + this.vsyncRate = vsyncRate; + } + + @Override + public String toString() { + return "SupportedModeData{" + + "refreshRate= " + refreshRate + + ", vsyncRate= " + vsyncRate + + '}'; + } + + static List<SupportedModeData> load(@Nullable NonNegativeFloatToFloatMap configMap) { + ArrayList<SupportedModeData> supportedModes = new ArrayList<>(); + if (configMap != null) { + for (NonNegativeFloatToFloatPoint supportedMode : configMap.getPoint()) { + supportedModes.add(new SupportedModeData(supportedMode.getFirst().floatValue(), + supportedMode.getSecond().floatValue())); + } + } + return supportedModes; + } +} diff --git a/services/core/java/com/android/server/display/mode/DisplayModeDirector.java b/services/core/java/com/android/server/display/mode/DisplayModeDirector.java index 91bd80eb9037..846ee238499a 100644 --- a/services/core/java/com/android/server/display/mode/DisplayModeDirector.java +++ b/services/core/java/com/android/server/display/mode/DisplayModeDirector.java @@ -78,6 +78,7 @@ import com.android.server.LocalServices; import com.android.server.display.DisplayDeviceConfig; import com.android.server.display.config.IdleScreenRefreshRateTimeoutLuxThresholdPoint; import com.android.server.display.config.RefreshRateData; +import com.android.server.display.config.SupportedModeData; import com.android.server.display.feature.DeviceConfigParameterProvider; import com.android.server.display.feature.DisplayManagerFlags; import com.android.server.display.utils.AmbientFilter; @@ -451,15 +452,6 @@ public class DisplayModeDirector { return config != null && config.isVrrSupportEnabled(); } - private boolean isVrrSupportedByAnyDisplayLocked() { - for (int i = 0; i < mDisplayDeviceConfigByDisplay.size(); i++) { - if (mDisplayDeviceConfigByDisplay.valueAt(i).isVrrSupportEnabled()) { - return true; - } - } - return false; - } - /** * Sets the desiredDisplayModeSpecsListener for changes to display mode and refresh rate ranges. */ @@ -939,18 +931,44 @@ public class DisplayModeDirector { private final Uri mMatchContentFrameRateSetting = Settings.Secure.getUriFor(Settings.Secure.MATCH_CONTENT_FRAME_RATE); - private final boolean mVsynLowPowerVoteEnabled; + private final boolean mVsyncLowPowerVoteEnabled; private final boolean mPeakRefreshRatePhysicalLimitEnabled; private final Context mContext; + private final Handler mHandler; private float mDefaultPeakRefreshRate; private float mDefaultRefreshRate; + private boolean mIsLowPower = false; + + private final DisplayManager.DisplayListener mDisplayListener = + new DisplayManager.DisplayListener() { + @Override + public void onDisplayAdded(int displayId) { + synchronized (mLock) { + updateLowPowerModeAllowedModesLocked(); + } + } + + @Override + public void onDisplayRemoved(int displayId) { + mVotesStorage.updateVote(displayId, Vote.PRIORITY_LOW_POWER_MODE_MODES, + null); + } + + @Override + public void onDisplayChanged(int displayId) { + synchronized (mLock) { + updateLowPowerModeAllowedModesLocked(); + } + } + }; SettingsObserver(@NonNull Context context, @NonNull Handler handler, DisplayManagerFlags flags) { super(handler); mContext = context; - mVsynLowPowerVoteEnabled = flags.isVsyncLowPowerVoteEnabled(); + mHandler = handler; + mVsyncLowPowerVoteEnabled = flags.isVsyncLowPowerVoteEnabled(); mPeakRefreshRatePhysicalLimitEnabled = flags.isPeakRefreshRatePhysicalLimitEnabled(); // We don't want to load from the DeviceConfig while constructing since this leads to // a spike in the latency of DisplayManagerService startup. This happens because @@ -983,6 +1001,7 @@ public class DisplayModeDirector { UserHandle.USER_SYSTEM); cr.registerContentObserver(mMatchContentFrameRateSetting, false /*notifyDescendants*/, this); + mInjector.registerDisplayListener(mDisplayListener, mHandler); float deviceConfigDefaultPeakRefresh = mConfigParameterProvider.getPeakRefreshRateDefault(); @@ -995,6 +1014,7 @@ public class DisplayModeDirector { updateLowPowerModeSettingLocked(); updateModeSwitchingTypeSettingLocked(); } + } public void setDefaultRefreshRate(float refreshRate) { @@ -1061,23 +1081,36 @@ public class DisplayModeDirector { } private void updateLowPowerModeSettingLocked() { - boolean inLowPowerMode = Settings.Global.getInt(mContext.getContentResolver(), + mIsLowPower = Settings.Global.getInt(mContext.getContentResolver(), Settings.Global.LOW_POWER_MODE, 0 /*default*/) != 0; final Vote vote; - if (inLowPowerMode && mVsynLowPowerVoteEnabled && isVrrSupportedByAnyDisplayLocked()) { - vote = Vote.forSupportedRefreshRates(List.of( - new SupportedRefreshRatesVote.RefreshRates(/* peakRefreshRate= */ 60f, - /* vsyncRate= */ 240f), - new SupportedRefreshRatesVote.RefreshRates(/* peakRefreshRate= */ 60f, - /* vsyncRate= */ 60f) - )); - } else if (inLowPowerMode) { + if (mIsLowPower) { vote = Vote.forRenderFrameRates(0f, 60f); } else { vote = null; } - mVotesStorage.updateGlobalVote(Vote.PRIORITY_LOW_POWER_MODE, vote); - mBrightnessObserver.onLowPowerModeEnabledLocked(inLowPowerMode); + mVotesStorage.updateGlobalVote(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, vote); + mBrightnessObserver.onLowPowerModeEnabledLocked(mIsLowPower); + updateLowPowerModeAllowedModesLocked(); + } + + private void updateLowPowerModeAllowedModesLocked() { + if (!mVsyncLowPowerVoteEnabled) { + return; + } + if (mIsLowPower) { + for (int i = 0; i < mDisplayDeviceConfigByDisplay.size(); i++) { + DisplayDeviceConfig config = mDisplayDeviceConfigByDisplay.valueAt(i); + List<SupportedModeData> supportedModes = config + .getRefreshRateData().lowPowerSupportedModes; + mVotesStorage.updateVote( + mDisplayDeviceConfigByDisplay.keyAt(i), + Vote.PRIORITY_LOW_POWER_MODE_MODES, + Vote.forSupportedRefreshRates(supportedModes)); + } + } else { + mVotesStorage.removeAllVotesForPriority(Vote.PRIORITY_LOW_POWER_MODE_MODES); + } } /** diff --git a/services/core/java/com/android/server/display/mode/Vote.java b/services/core/java/com/android/server/display/mode/Vote.java index ddb334ee1a9d..8167c1fe1e91 100644 --- a/services/core/java/com/android/server/display/mode/Vote.java +++ b/services/core/java/com/android/server/display/mode/Vote.java @@ -18,6 +18,9 @@ package com.android.server.display.mode; import android.annotation.NonNull; +import com.android.server.display.config.SupportedModeData; + +import java.util.ArrayList; import java.util.List; interface Vote { @@ -102,9 +105,15 @@ interface Vote { // For internal application to limit display modes to specific ids int PRIORITY_SYSTEM_REQUESTED_MODES = 14; - // LOW_POWER_MODE force the render frame rate to [0, 60HZ] if + // PRIORITY_LOW_POWER_MODE_MODES limits display modes to specific refreshRate-vsync pairs if + // Settings.Global.LOW_POWER_MODE is on. + // Lower priority that PRIORITY_LOW_POWER_MODE_RENDER_RATE and if discarded (due to other + // higher priority votes), render rate limit can still apply + int PRIORITY_LOW_POWER_MODE_MODES = 14; + + // PRIORITY_LOW_POWER_MODE_RENDER_RATE force the render frame rate to [0, 60HZ] if // Settings.Global.LOW_POWER_MODE is on. - int PRIORITY_LOW_POWER_MODE = 15; + int PRIORITY_LOW_POWER_MODE_RENDER_RATE = 15; // PRIORITY_FLICKER_REFRESH_RATE_SWITCH votes for disabling refresh rate switching. If the // higher priority voters' result is a range, it will fix the rate to a single choice. @@ -177,22 +186,26 @@ interface Vote { return new BaseModeRefreshRateVote(baseModeRefreshRate); } - static Vote forSupportedRefreshRates( - List<SupportedRefreshRatesVote.RefreshRates> refreshRates) { - return new SupportedRefreshRatesVote(refreshRates); + static Vote forSupportedRefreshRates(List<SupportedModeData> supportedModes) { + if (supportedModes.isEmpty()) { + return null; + } + List<SupportedRefreshRatesVote.RefreshRates> rates = new ArrayList<>(); + for (SupportedModeData data : supportedModes) { + rates.add(new SupportedRefreshRatesVote.RefreshRates(data.refreshRate, data.vsyncRate)); + } + return new SupportedRefreshRatesVote(rates); } static Vote forSupportedModes(List<Integer> modeIds) { return new SupportedModesVote(modeIds); } - - static Vote forSupportedRefreshRatesAndDisableSwitching( List<SupportedRefreshRatesVote.RefreshRates> supportedRefreshRates) { return new CombinedVote( List.of(forDisableRefreshRateSwitching(), - forSupportedRefreshRates(supportedRefreshRates))); + new SupportedRefreshRatesVote(supportedRefreshRates))); } static String priorityToString(int priority) { @@ -213,8 +226,10 @@ interface Vote { return "PRIORITY_HIGH_BRIGHTNESS_MODE"; case PRIORITY_PROXIMITY: return "PRIORITY_PROXIMITY"; - case PRIORITY_LOW_POWER_MODE: - return "PRIORITY_LOW_POWER_MODE"; + case PRIORITY_LOW_POWER_MODE_MODES: + return "PRIORITY_LOW_POWER_MODE_MODES"; + case PRIORITY_LOW_POWER_MODE_RENDER_RATE: + return "PRIORITY_LOW_POWER_MODE_RENDER_RATE"; case PRIORITY_SKIN_TEMPERATURE: return "PRIORITY_SKIN_TEMPERATURE"; case PRIORITY_UDFPS: @@ -227,6 +242,8 @@ interface Vote { return "PRIORITY_LIMIT_MODE"; case PRIORITY_SYNCHRONIZED_REFRESH_RATE: return "PRIORITY_SYNCHRONIZED_REFRESH_RATE"; + case PRIORITY_USER_SETTING_PEAK_REFRESH_RATE: + return "PRIORITY_USER_SETTING_PEAK_REFRESH_RATE"; case PRIORITY_USER_SETTING_PEAK_RENDER_FRAME_RATE: return "PRIORITY_USER_SETTING_PEAK_RENDER_FRAME_RATE"; case PRIORITY_AUTH_OPTIMIZER_RENDER_FRAME_RATE: diff --git a/services/core/xsd/display-device-config/display-device-config.xsd b/services/core/xsd/display-device-config/display-device-config.xsd index 6143f1dd5b1c..610b502f2a07 100644 --- a/services/core/xsd/display-device-config/display-device-config.xsd +++ b/services/core/xsd/display-device-config/display-device-config.xsd @@ -746,6 +746,20 @@ minOccurs="0" maxOccurs="1"> <xs:annotation name="final"/> </xs:element> + <!-- list of supported modes for low power. Each point corresponds to one mode. + Mode format is : first = refreshRate, second = vsyncRate. E.g. : + <lowPowerSupportedModes> + <point> + <first>60</first> // refreshRate + <second>60</second> //vsyncRate + </point> + .... + </lowPowerSupportedModes> + --> + <xs:element type="nonNegativeFloatToFloatMap" name="lowPowerSupportedModes" minOccurs="0"> + <xs:annotation name="nullable"/> + <xs:annotation name="final"/> + </xs:element> </xs:complexType> <xs:complexType name="refreshRateZoneProfiles"> diff --git a/services/core/xsd/display-device-config/schema/current.txt b/services/core/xsd/display-device-config/schema/current.txt index 45ec8f250efa..203a6d99dba1 100644 --- a/services/core/xsd/display-device-config/schema/current.txt +++ b/services/core/xsd/display-device-config/schema/current.txt @@ -360,6 +360,7 @@ package com.android.server.display.config { method public final java.math.BigInteger getDefaultRefreshRateInHbmHdr(); method public final java.math.BigInteger getDefaultRefreshRateInHbmSunlight(); method public final com.android.server.display.config.BlockingZoneConfig getHigherBlockingZoneConfigs(); + method @Nullable public final com.android.server.display.config.NonNegativeFloatToFloatMap getLowPowerSupportedModes(); method public final com.android.server.display.config.BlockingZoneConfig getLowerBlockingZoneConfigs(); method public final com.android.server.display.config.RefreshRateZoneProfiles getRefreshRateZoneProfiles(); method public final void setDefaultPeakRefreshRate(java.math.BigInteger); @@ -367,6 +368,7 @@ package com.android.server.display.config { method public final void setDefaultRefreshRateInHbmHdr(java.math.BigInteger); method public final void setDefaultRefreshRateInHbmSunlight(java.math.BigInteger); method public final void setHigherBlockingZoneConfigs(com.android.server.display.config.BlockingZoneConfig); + method public final void setLowPowerSupportedModes(@Nullable com.android.server.display.config.NonNegativeFloatToFloatMap); method public final void setLowerBlockingZoneConfigs(com.android.server.display.config.BlockingZoneConfig); method public final void setRefreshRateZoneProfiles(com.android.server.display.config.RefreshRateZoneProfiles); } diff --git a/services/tests/displayservicetests/src/com/android/server/display/DisplayDeviceConfigTest.java b/services/tests/displayservicetests/src/com/android/server/display/DisplayDeviceConfigTest.java index a0a611ff4eb1..46d08b0ce018 100644 --- a/services/tests/displayservicetests/src/com/android/server/display/DisplayDeviceConfigTest.java +++ b/services/tests/displayservicetests/src/com/android/server/display/DisplayDeviceConfigTest.java @@ -21,7 +21,6 @@ import static com.android.internal.display.BrightnessSynchronizer.brightnessIntT import static com.android.server.display.AutomaticBrightnessController.AUTO_BRIGHTNESS_MODE_DEFAULT; import static com.android.server.display.AutomaticBrightnessController.AUTO_BRIGHTNESS_MODE_DOZE; import static com.android.server.display.config.SensorData.TEMPERATURE_TYPE_SKIN; -import static com.android.server.display.config.SensorData.SupportedMode; import static com.android.server.display.utils.DeviceConfigParsingUtils.ambientBrightnessThresholdsIntToFloat; import static com.android.server.display.utils.DeviceConfigParsingUtils.displayBrightnessThresholdsIntToFloat; @@ -58,6 +57,7 @@ import com.android.server.display.config.HdrBrightnessData; import com.android.server.display.config.HysteresisLevels; import com.android.server.display.config.IdleScreenRefreshRateTimeoutLuxThresholdPoint; import com.android.server.display.config.RefreshRateData; +import com.android.server.display.config.SupportedModeData; import com.android.server.display.config.ThermalStatus; import com.android.server.display.feature.DisplayManagerFlags; import com.android.server.display.feature.flags.Flags; @@ -613,7 +613,7 @@ public final class DisplayDeviceConfigTest { assertEquals(mDisplayDeviceConfig.getProximitySensor().minRefreshRate, 60, SMALL_DELTA); assertEquals(mDisplayDeviceConfig.getProximitySensor().maxRefreshRate, 90, SMALL_DELTA); assertThat(mDisplayDeviceConfig.getProximitySensor().supportedModes).hasSize(2); - SupportedMode mode = mDisplayDeviceConfig.getProximitySensor().supportedModes.get(0); + SupportedModeData mode = mDisplayDeviceConfig.getProximitySensor().supportedModes.get(0); assertEquals(mode.refreshRate, 60, SMALL_DELTA); assertEquals(mode.vsyncRate, 65, SMALL_DELTA); mode = mDisplayDeviceConfig.getProximitySensor().supportedModes.get(1); @@ -933,6 +933,21 @@ public final class DisplayDeviceConfigTest { assertEquals(0.2f, mDisplayDeviceConfig.getNitsFromBacklight(0.0f), ZERO_DELTA); } + @Test + public void testLowPowerSupportedModesFromConfigFile() throws IOException { + setupDisplayDeviceConfigFromDisplayConfigFile(); + + RefreshRateData refreshRateData = mDisplayDeviceConfig.getRefreshRateData(); + assertNotNull(refreshRateData); + assertThat(refreshRateData.lowPowerSupportedModes).hasSize(2); + SupportedModeData supportedModeData = refreshRateData.lowPowerSupportedModes.get(0); + assertThat(supportedModeData.refreshRate).isEqualTo(60); + assertThat(supportedModeData.vsyncRate).isEqualTo(60); + supportedModeData = refreshRateData.lowPowerSupportedModes.get(1); + assertThat(supportedModeData.refreshRate).isEqualTo(60); + assertThat(supportedModeData.vsyncRate).isEqualTo(120); + } + private String getValidLuxThrottling() { return "<luxThrottling>\n" + " <brightnessLimitMap>\n" @@ -1089,6 +1104,19 @@ public final class DisplayDeviceConfigTest { + "</proxSensor>\n"; } + private String getLowPowerConfig() { + return "<lowPowerSupportedModes>\n" + + " <point>\n" + + " <first>60</first>\n" + + " <second>60</second>\n" + + " </point>\n" + + " <point>\n" + + " <first>60</first>\n" + + " <second>120</second>\n" + + " </point>\n" + + "</lowPowerSupportedModes>\n"; + } + private String getHdrBrightnessConfig() { return "<hdrBrightnessConfig>\n" + " <brightnessMap>\n" @@ -1620,6 +1648,7 @@ public final class DisplayDeviceConfigTest { + "</displayBrightnessPoint>\n" + "</blockingZoneThreshold>\n" + "</higherBlockingZoneConfigs>\n" + + getLowPowerConfig() + "</refreshRate>\n" + "<screenOffBrightnessSensorValueToLux>\n" + "<item>-1</item>\n" diff --git a/services/tests/displayservicetests/src/com/android/server/display/mode/DisplayModeDirectorTest.java b/services/tests/displayservicetests/src/com/android/server/display/mode/DisplayModeDirectorTest.java index cd1e9e85afb5..714b423fae70 100644 --- a/services/tests/displayservicetests/src/com/android/server/display/mode/DisplayModeDirectorTest.java +++ b/services/tests/displayservicetests/src/com/android/server/display/mode/DisplayModeDirectorTest.java @@ -131,7 +131,8 @@ public class DisplayModeDirectorTest { /* defaultRefreshRate= */ 0, /* defaultPeakRefreshRate= */ 0, /* defaultRefreshRateInHbmHdr= */ 0, - /* defaultRefreshRateInHbmSunlight= */ 0); + /* defaultRefreshRateInHbmSunlight= */ 0, + /* lowPowerSupportedModes =*/ List.of()); public static Collection<Object[]> getAppRequestedSizeTestCases() { var appRequestedSizeTestCases = Arrays.asList(new Object[][] { @@ -157,7 +158,7 @@ public class DisplayModeDirectorTest { APP_MODE_HIGH_90.getPhysicalHeight()), Vote.PRIORITY_APP_REQUEST_BASE_MODE_REFRESH_RATE, Vote.forBaseModeRefreshRate(APP_MODE_HIGH_90.getRefreshRate()), - Vote.PRIORITY_LOW_POWER_MODE, + Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forSize(LIMIT_MODE_70.getPhysicalWidth(), LIMIT_MODE_70.getPhysicalHeight()))}, {/*expectedBaseModeId*/ LIMIT_MODE_70.getModeId(), @@ -169,7 +170,7 @@ public class DisplayModeDirectorTest { APP_MODE_65.getPhysicalHeight()), Vote.PRIORITY_APP_REQUEST_BASE_MODE_REFRESH_RATE, Vote.forBaseModeRefreshRate(APP_MODE_65.getRefreshRate()), - Vote.PRIORITY_LOW_POWER_MODE, + Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forSize(LIMIT_MODE_70.getPhysicalWidth(), LIMIT_MODE_70.getPhysicalHeight()))}, {/*expectedBaseModeId*/ LIMIT_MODE_70.getModeId(), @@ -181,7 +182,7 @@ public class DisplayModeDirectorTest { APP_MODE_65.getPhysicalHeight()), Vote.PRIORITY_APP_REQUEST_BASE_MODE_REFRESH_RATE, Vote.forBaseModeRefreshRate(APP_MODE_65.getRefreshRate()), - Vote.PRIORITY_LOW_POWER_MODE, + Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forSizeAndPhysicalRefreshRatesRange( 0, 0, LIMIT_MODE_70.getPhysicalWidth(), @@ -197,7 +198,7 @@ public class DisplayModeDirectorTest { APP_MODE_65.getPhysicalHeight()), Vote.PRIORITY_APP_REQUEST_BASE_MODE_REFRESH_RATE, Vote.forBaseModeRefreshRate(APP_MODE_65.getRefreshRate()), - Vote.PRIORITY_LOW_POWER_MODE, + Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forSizeAndPhysicalRefreshRatesRange( 0, 0, LIMIT_MODE_70.getPhysicalWidth(), @@ -213,7 +214,7 @@ public class DisplayModeDirectorTest { APP_MODE_HIGH_90.getPhysicalHeight()), Vote.PRIORITY_APP_REQUEST_BASE_MODE_REFRESH_RATE, Vote.forBaseModeRefreshRate(APP_MODE_HIGH_90.getRefreshRate()), - Vote.PRIORITY_LOW_POWER_MODE, + Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forSizeAndPhysicalRefreshRatesRange( 0, 0, LIMIT_MODE_70.getPhysicalWidth(), @@ -229,7 +230,7 @@ public class DisplayModeDirectorTest { APP_MODE_HIGH_90.getPhysicalHeight()), Vote.PRIORITY_APP_REQUEST_BASE_MODE_REFRESH_RATE, Vote.forBaseModeRefreshRate(APP_MODE_HIGH_90.getRefreshRate()), - Vote.PRIORITY_LOW_POWER_MODE, + Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forSizeAndPhysicalRefreshRatesRange( 0, 0, LIMIT_MODE_70.getPhysicalWidth(), @@ -245,7 +246,7 @@ public class DisplayModeDirectorTest { Vote.PRIORITY_APP_REQUEST_SIZE, Vote.forSize(APP_MODE_65.getPhysicalWidth(), APP_MODE_65.getPhysicalHeight()), - Vote.PRIORITY_LOW_POWER_MODE, + Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forPhysicalRefreshRates( 0, 64.99f))}}); @@ -598,7 +599,7 @@ public class DisplayModeDirectorTest { < Vote.PRIORITY_APP_REQUEST_SIZE); assertTrue(Vote.PRIORITY_FLICKER_REFRESH_RATE_SWITCH - > Vote.PRIORITY_LOW_POWER_MODE); + > Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE); Display.Mode[] modes = new Display.Mode[4]; modes[0] = new Display.Mode( @@ -676,9 +677,9 @@ public class DisplayModeDirectorTest { @Test public void testLPMHasHigherPriorityThanUser() { - assertTrue(Vote.PRIORITY_LOW_POWER_MODE + assertTrue(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE > Vote.PRIORITY_APP_REQUEST_BASE_MODE_REFRESH_RATE); - assertTrue(Vote.PRIORITY_LOW_POWER_MODE + assertTrue(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE > Vote.PRIORITY_APP_REQUEST_SIZE); Display.Mode[] modes = new Display.Mode[4]; @@ -700,7 +701,7 @@ public class DisplayModeDirectorTest { Vote.forBaseModeRefreshRate(appRequestedMode.getRefreshRate())); votes.put(Vote.PRIORITY_APP_REQUEST_SIZE, Vote.forSize(appRequestedMode.getPhysicalWidth(), appRequestedMode.getPhysicalHeight())); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(60, 60)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(60, 60)); director.injectVotesByDisplay(votesByDisplay); DesiredDisplayModeSpecs desiredSpecs = director.getDesiredDisplayModeSpecs(DISPLAY_ID); assertThat(desiredSpecs.baseModeId).isEqualTo(2); @@ -715,7 +716,7 @@ public class DisplayModeDirectorTest { Vote.forBaseModeRefreshRate(appRequestedMode.getRefreshRate())); votes.put(Vote.PRIORITY_APP_REQUEST_SIZE, Vote.forSize(appRequestedMode.getPhysicalWidth(), appRequestedMode.getPhysicalHeight())); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(90, 90)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(90, 90)); director.injectVotesByDisplay(votesByDisplay); desiredSpecs = director.getDesiredDisplayModeSpecs(DISPLAY_ID); assertThat(desiredSpecs.baseModeId).isEqualTo(4); @@ -730,7 +731,7 @@ public class DisplayModeDirectorTest { Vote.forBaseModeRefreshRate(appRequestedMode.getRefreshRate())); votes.put(Vote.PRIORITY_APP_REQUEST_SIZE, Vote.forSize(appRequestedMode.getPhysicalWidth(), appRequestedMode.getPhysicalHeight())); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(60, 60)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(60, 60)); director.injectVotesByDisplay(votesByDisplay); desiredSpecs = director.getDesiredDisplayModeSpecs(DISPLAY_ID); assertThat(desiredSpecs.baseModeId).isEqualTo(2); @@ -745,7 +746,7 @@ public class DisplayModeDirectorTest { Vote.forBaseModeRefreshRate(appRequestedMode.getRefreshRate())); votes.put(Vote.PRIORITY_APP_REQUEST_SIZE, Vote.forSize(appRequestedMode.getPhysicalWidth(), appRequestedMode.getPhysicalHeight())); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(90, 90)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(90, 90)); director.injectVotesByDisplay(votesByDisplay); desiredSpecs = director.getDesiredDisplayModeSpecs(DISPLAY_ID); assertThat(desiredSpecs.baseModeId).isEqualTo(4); @@ -906,7 +907,7 @@ public class DisplayModeDirectorTest { Vote.forBaseModeRefreshRate(appRequestedMode.getRefreshRate())); votes.put(Vote.PRIORITY_USER_SETTING_PEAK_RENDER_FRAME_RATE, Vote.forRenderFrameRates(60, 60)); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 60)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 60)); director.injectVotesByDisplay(votesByDisplay); assertThat(director.shouldAlwaysRespectAppRequestedMode()).isFalse(); @@ -946,7 +947,7 @@ public class DisplayModeDirectorTest { votesByDisplay.put(DISPLAY_ID, votes); votes.put(Vote.PRIORITY_USER_SETTING_MIN_RENDER_FRAME_RATE, Vote.forRenderFrameRates(30, 90)); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 60)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 60)); director.injectVotesByDisplay(votesByDisplay); assertThat(director.getModeSwitchingType()) @@ -987,7 +988,7 @@ public class DisplayModeDirectorTest { votesByDisplay.put(DISPLAY_ID, votes); votes.put(Vote.PRIORITY_USER_SETTING_MIN_RENDER_FRAME_RATE, Vote.forRenderFrameRates(30, 90)); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 60)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 60)); director.injectVotesByDisplay(votesByDisplay); assertThat(director.getModeSwitchingType()) @@ -1029,7 +1030,7 @@ public class DisplayModeDirectorTest { votesByDisplay.put(DISPLAY_ID, votes); votes.put(Vote.PRIORITY_USER_SETTING_MIN_RENDER_FRAME_RATE, Vote.forRenderFrameRates(30, 90)); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 60)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 60)); director.injectVotesByDisplay(votesByDisplay); assertThat(director.getModeSwitchingType()) @@ -1900,7 +1901,7 @@ public class DisplayModeDirectorTest { director.start(createMockSensorManager()); SparseArray<Vote> votes = new SparseArray<>(); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 50f)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 50f)); SparseArray<SparseArray<Vote>> votesByDisplay = new SparseArray<>(); votesByDisplay.put(DISPLAY_ID_2, votes); @@ -2298,7 +2299,7 @@ public class DisplayModeDirectorTest { votes.put(Vote.PRIORITY_USER_SETTING_MIN_RENDER_FRAME_RATE, Vote.forRenderFrameRates(90, Float.POSITIVE_INFINITY)); votes.put(Vote.PRIORITY_FLICKER_REFRESH_RATE_SWITCH, Vote.forDisableRefreshRateSwitching()); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 60)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 60)); director.injectVotesByDisplay(votesByDisplay); DesiredDisplayModeSpecs desiredSpecs = director.getDesiredDisplayModeSpecs(DISPLAY_ID); assertThat(desiredSpecs.primary.physical.min).isWithin(FLOAT_TOLERANCE).of(50); @@ -2311,7 +2312,7 @@ public class DisplayModeDirectorTest { votes.put(Vote.PRIORITY_USER_SETTING_MIN_RENDER_FRAME_RATE, Vote.forRenderFrameRates(80, Float.POSITIVE_INFINITY)); votes.put(Vote.PRIORITY_FLICKER_REFRESH_RATE_SWITCH, Vote.forDisableRefreshRateSwitching()); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 90)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 90)); desiredSpecs = director.getDesiredDisplayModeSpecs(DISPLAY_ID); assertThat(desiredSpecs.primary.physical.min).isWithin(FLOAT_TOLERANCE).of(80); assertThat(desiredSpecs.primary.physical.max).isWithin(FLOAT_TOLERANCE).of(80); @@ -2323,7 +2324,7 @@ public class DisplayModeDirectorTest { votes.put(Vote.PRIORITY_USER_SETTING_MIN_RENDER_FRAME_RATE, Vote.forRenderFrameRates(80, Float.POSITIVE_INFINITY)); votes.put(Vote.PRIORITY_FLICKER_REFRESH_RATE_SWITCH, Vote.forDisableRefreshRateSwitching()); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 90)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 90)); desiredSpecs = director.getDesiredDisplayModeSpecs(DISPLAY_ID); assertThat(desiredSpecs.primary.physical.min).isWithin(FLOAT_TOLERANCE).of(90); assertThat(desiredSpecs.primary.physical.max).isWithin(FLOAT_TOLERANCE).of(90); @@ -2343,7 +2344,7 @@ public class DisplayModeDirectorTest { votesByDisplay.put(DISPLAY_ID, votes); votes.put(Vote.PRIORITY_APP_REQUEST_BASE_MODE_REFRESH_RATE, Vote.forBaseModeRefreshRate(70)); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 60)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 60)); director.injectVotesByDisplay(votesByDisplay); DesiredDisplayModeSpecs desiredSpecs = director.getDesiredDisplayModeSpecs(DISPLAY_ID); assertThat(desiredSpecs.primary.physical.min).isWithin(FLOAT_TOLERANCE).of(0); @@ -2360,7 +2361,7 @@ public class DisplayModeDirectorTest { votes.clear(); votes.put(Vote.PRIORITY_APP_REQUEST_BASE_MODE_REFRESH_RATE, Vote.forBaseModeRefreshRate(55)); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 60)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 60)); director.injectVotesByDisplay(votesByDisplay); desiredSpecs = director.getDesiredDisplayModeSpecs(DISPLAY_ID); assertThat(desiredSpecs.primary.physical.min).isWithin(FLOAT_TOLERANCE).of(0); @@ -2374,7 +2375,7 @@ public class DisplayModeDirectorTest { Vote.forRenderFrameRates(0, 52)); votes.put(Vote.PRIORITY_APP_REQUEST_BASE_MODE_REFRESH_RATE, Vote.forBaseModeRefreshRate(55)); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 60)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 60)); director.injectVotesByDisplay(votesByDisplay); desiredSpecs = director.getDesiredDisplayModeSpecs(DISPLAY_ID); assertThat(desiredSpecs.primary.physical.min).isWithin(FLOAT_TOLERANCE).of(0); @@ -2392,7 +2393,7 @@ public class DisplayModeDirectorTest { Vote.forRenderFrameRates(0, 58)); votes.put(Vote.PRIORITY_APP_REQUEST_BASE_MODE_REFRESH_RATE, Vote.forBaseModeRefreshRate(55)); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 60)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 60)); director.injectVotesByDisplay(votesByDisplay); desiredSpecs = director.getDesiredDisplayModeSpecs(DISPLAY_ID); assertThat(desiredSpecs.primary.physical.min).isWithin(FLOAT_TOLERANCE).of(0); @@ -2521,7 +2522,7 @@ public class DisplayModeDirectorTest { votes.put(Vote.PRIORITY_UDFPS, Vote.forPhysicalRefreshRates(120, 120)); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(90, 90)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(90, 90)); director.injectVotesByDisplay(votesByDisplay); DesiredDisplayModeSpecs desiredSpecs = director.getDesiredDisplayModeSpecs(DISPLAY_ID); assertThat(desiredSpecs.appRequest.physical.min).isWithin(FLOAT_TOLERANCE).of(120); @@ -2542,7 +2543,7 @@ public class DisplayModeDirectorTest { SparseArray<SparseArray<Vote>> votesByDisplay = new SparseArray<>(); votesByDisplay.put(DISPLAY_ID, votes); - votes.put(Vote.PRIORITY_LOW_POWER_MODE, Vote.forRenderFrameRates(0, 60)); + votes.put(Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE, Vote.forRenderFrameRates(0, 60)); votes.put(Vote.PRIORITY_USER_SETTING_PEAK_RENDER_FRAME_RATE, Vote.forRenderFrameRates(0, 30)); director.injectVotesByDisplay(votesByDisplay); @@ -3168,7 +3169,8 @@ public class DisplayModeDirectorTest { /* defaultRefreshRate= */ 60, /* defaultPeakRefreshRate= */ 65, /* defaultRefreshRateInHbmHdr= */ 65, - /* defaultRefreshRateInHbmSunlight= */ 75); + /* defaultRefreshRateInHbmSunlight= */ 75, + /* lowPowerSupportedModes= */ List.of()); when(displayDeviceConfig.getRefreshRateData()).thenReturn(refreshRateData); when(displayDeviceConfig.getDefaultLowBlockingZoneRefreshRate()).thenReturn(50); when(displayDeviceConfig.getDefaultHighBlockingZoneRefreshRate()).thenReturn(55); @@ -3390,9 +3392,10 @@ public class DisplayModeDirectorTest { ArgumentCaptor<DisplayListener> displayListenerCaptor = ArgumentCaptor.forClass(DisplayListener.class); - verify(mInjector).registerDisplayListener(displayListenerCaptor.capture(), + verify(mInjector, atLeastOnce()).registerDisplayListener(displayListenerCaptor.capture(), any(Handler.class)); - DisplayListener displayListener = displayListenerCaptor.getValue(); + // DisplayObserver should register first + DisplayListener displayListener = displayListenerCaptor.getAllValues().get(0); float refreshRate = 60; mInjector.mDisplayInfo.layoutLimitedRefreshRate = @@ -3417,9 +3420,10 @@ public class DisplayModeDirectorTest { ArgumentCaptor<DisplayListener> displayListenerCaptor = ArgumentCaptor.forClass(DisplayListener.class); - verify(mInjector).registerDisplayListener(displayListenerCaptor.capture(), + verify(mInjector, atLeastOnce()).registerDisplayListener(displayListenerCaptor.capture(), any(Handler.class)); - DisplayListener displayListener = displayListenerCaptor.getValue(); + // DisplayObserver should register first + DisplayListener displayListener = displayListenerCaptor.getAllValues().get(0); mInjector.mDisplayInfo.layoutLimitedRefreshRate = new RefreshRateRange(10, 10); mInjector.mDisplayInfoValid = false; diff --git a/services/tests/displayservicetests/src/com/android/server/display/mode/DisplayObserverTest.java b/services/tests/displayservicetests/src/com/android/server/display/mode/DisplayObserverTest.java index 2d317af3d85d..ee79d196cfd9 100644 --- a/services/tests/displayservicetests/src/com/android/server/display/mode/DisplayObserverTest.java +++ b/services/tests/displayservicetests/src/com/android/server/display/mode/DisplayObserverTest.java @@ -407,7 +407,8 @@ public class DisplayObserverTest { assertThat(mObserver).isNull(); mObserver = invocation.getArgument(0); return null; - }).when(mInjector).registerDisplayListener(any(), any()); + }).when(mInjector).registerDisplayListener( + any(DisplayModeDirector.DisplayObserver.class), any()); doAnswer(c -> { DisplayInfo info = c.getArgument(1); diff --git a/services/tests/displayservicetests/src/com/android/server/display/mode/SettingsObserverTest.kt b/services/tests/displayservicetests/src/com/android/server/display/mode/SettingsObserverTest.kt index 4d910cefdb79..e431c8c3555c 100644 --- a/services/tests/displayservicetests/src/com/android/server/display/mode/SettingsObserverTest.kt +++ b/services/tests/displayservicetests/src/com/android/server/display/mode/SettingsObserverTest.kt @@ -27,8 +27,11 @@ import androidx.test.core.app.ApplicationProvider import androidx.test.filters.SmallTest import com.android.internal.util.test.FakeSettingsProvider import com.android.server.display.DisplayDeviceConfig +import com.android.server.display.config.RefreshRateData +import com.android.server.display.config.SupportedModeData import com.android.server.display.feature.DisplayManagerFlags import com.android.server.display.mode.DisplayModeDirector.DisplayDeviceConfigProvider +import com.android.server.display.mode.SupportedRefreshRatesVote.RefreshRates import com.android.server.testutils.TestHandler import com.google.common.truth.Truth.assertThat import com.google.common.truth.Truth.assertWithMessage @@ -69,6 +72,13 @@ private val RANGES_MIN90_90TO120 = RefreshRateRanges(RANGE_90_INF, RANGE_90_120) private val RANGES_MIN60_60TO90 = RefreshRateRanges(RANGE_60_INF, RANGE_60_90) private val RANGES_MIN90_90TO90 = RefreshRateRanges(RANGE_90_INF, RANGE_90_90) +private val LOW_POWER_GLOBAL_VOTE = Vote.forRenderFrameRates(0f, 60f) +private val LOW_POWER_REFRESH_RATE_DATA = createRefreshRateData( + lowPowerSupportedModes = listOf(SupportedModeData(60f, 60f), SupportedModeData(60f, 240f))) +private val LOW_POWER_EMPTY_REFRESH_RATE_DATA = createRefreshRateData() +private val EXPECTED_SUPPORTED_MODES_VOTE = SupportedRefreshRatesVote( + listOf(RefreshRates(60f, 60f), RefreshRates(60f, 240f))) + @SmallTest @RunWith(TestParameterInjector::class) class SettingsObserverTest { @@ -103,7 +113,7 @@ class SettingsObserverTest { val displayModeDirector = DisplayModeDirector( spyContext, testHandler, mockInjector, mockFlags, mockDisplayDeviceConfigProvider) val ddcByDisplay = SparseArray<DisplayDeviceConfig>() - whenever(mockDeviceConfig.isVrrSupportEnabled).thenReturn(testCase.vrrSupported) + whenever(mockDeviceConfig.refreshRateData).thenReturn(testCase.refreshRateData) ddcByDisplay.put(Display.DEFAULT_DISPLAY, mockDeviceConfig) displayModeDirector.injectDisplayDeviceConfigByDisplay(ddcByDisplay) val settingsObserver = displayModeDirector.SettingsObserver( @@ -113,27 +123,30 @@ class SettingsObserverTest { false, Settings.Global.getUriFor(Settings.Global.LOW_POWER_MODE), 1) assertThat(displayModeDirector.getVote(VotesStorage.GLOBAL_ID, - Vote.PRIORITY_LOW_POWER_MODE)).isEqualTo(testCase.expectedVote) + Vote.PRIORITY_LOW_POWER_MODE_RENDER_RATE)).isEqualTo(testCase.globalVote) + assertThat(displayModeDirector.getVote(Display.DEFAULT_DISPLAY, + Vote.PRIORITY_LOW_POWER_MODE_MODES)).isEqualTo(testCase.displayVote) } enum class LowPowerTestCase( - val vrrSupported: Boolean, + val refreshRateData: RefreshRateData, val vsyncLowPowerVoteEnabled: Boolean, val lowPowerModeEnabled: Boolean, - internal val expectedVote: Vote? + internal val globalVote: Vote?, + internal val displayVote: Vote? ) { - ALL_ENABLED(true, true, true, - SupportedRefreshRatesVote(listOf( - SupportedRefreshRatesVote.RefreshRates(60f, 240f), - SupportedRefreshRatesVote.RefreshRates(60f, 60f) - ))), - LOW_POWER_OFF(true, true, false, null), - DVRR_NOT_SUPPORTED_LOW_POWER_ON(false, true, true, - RefreshRateVote.RenderVote(0f, 60f)), - DVRR_NOT_SUPPORTED_LOW_POWER_OFF(false, true, false, null), - VSYNC_VOTE_DISABLED_SUPPORTED_LOW_POWER_ON(true, false, true, - RefreshRateVote.RenderVote(0f, 60f)), - VSYNC_VOTE_DISABLED_LOW_POWER_OFF(true, false, false, null), + ALL_ENABLED(LOW_POWER_REFRESH_RATE_DATA, true, true, + LOW_POWER_GLOBAL_VOTE, EXPECTED_SUPPORTED_MODES_VOTE), + LOW_POWER_OFF(LOW_POWER_REFRESH_RATE_DATA, true, false, + null, null), + EMPTY_REFRESH_LOW_POWER_ON(LOW_POWER_EMPTY_REFRESH_RATE_DATA, true, true, + LOW_POWER_GLOBAL_VOTE, null), + EMPTY_REFRESH__LOW_POWER_OFF(LOW_POWER_EMPTY_REFRESH_RATE_DATA, true, false, + null, null), + VSYNC_VOTE_DISABLED_SUPPORTED_LOW_POWER_ON(LOW_POWER_REFRESH_RATE_DATA, false, true, + LOW_POWER_GLOBAL_VOTE, null), + VSYNC_VOTE_DISABLED_LOW_POWER_OFF(LOW_POWER_REFRESH_RATE_DATA, false, false, + null, null), } @Test diff --git a/services/tests/displayservicetests/src/com/android/server/display/mode/TestUtils.kt b/services/tests/displayservicetests/src/com/android/server/display/mode/TestUtils.kt index 6b90bde188c5..1206e30b9e88 100644 --- a/services/tests/displayservicetests/src/com/android/server/display/mode/TestUtils.kt +++ b/services/tests/displayservicetests/src/com/android/server/display/mode/TestUtils.kt @@ -16,6 +16,9 @@ package com.android.server.display.mode +import com.android.server.display.config.RefreshRateData +import com.android.server.display.config.SupportedModeData + internal fun createVotesSummary( isDisplayResolutionRangeVotingEnabled: Boolean = true, supportedModesVoteEnabled: Boolean = true, @@ -24,4 +27,16 @@ internal fun createVotesSummary( ): VoteSummary { return VoteSummary(isDisplayResolutionRangeVotingEnabled, supportedModesVoteEnabled, loggingEnabled, supportsFrameRateOverride) -}
\ No newline at end of file +} + +fun createRefreshRateData( + defaultRefreshRate: Int = 60, + defaultPeakRefreshRate: Int = 60, + defaultRefreshRateInHbmHdr: Int = 60, + defaultRefreshRateInHbmSunlight: Int = 60, + lowPowerSupportedModes: List<SupportedModeData> = emptyList() +): RefreshRateData { + return RefreshRateData(defaultRefreshRate, defaultPeakRefreshRate, + defaultRefreshRateInHbmHdr, defaultRefreshRateInHbmSunlight, + lowPowerSupportedModes) +} |