Allow sensors to be specified per display

Add a field in display device configurations that allows sensors to be stored.
Read the sensor type and name through dpc.

Bug: 128782163
Test: manual
Change-Id: I4cd778fca085b398b21457104a6a58ad0dae46e2
diff --git a/services/core/java/com/android/server/display/DisplayDeviceConfig.java b/services/core/java/com/android/server/display/DisplayDeviceConfig.java
index 0071b2f..ace466a 100644
--- a/services/core/java/com/android/server/display/DisplayDeviceConfig.java
+++ b/services/core/java/com/android/server/display/DisplayDeviceConfig.java
@@ -34,6 +34,7 @@
 import com.android.server.display.config.HighBrightnessMode;
 import com.android.server.display.config.NitsMap;
 import com.android.server.display.config.Point;
+import com.android.server.display.config.SensorDetails;
 import com.android.server.display.config.XmlParser;
 
 import org.xmlpull.v1.XmlPullParserException;
@@ -75,6 +76,9 @@
 
     private final Context mContext;
 
+    // The details of the ambient light sensor associated with this display.
+    private final SensorIdentifier mAmbientLightSensor = new SensorIdentifier();
+
     // Nits and backlight values that are loaded from either the display device config file, or
     // config.xml. These are the raw values and just used for the dumpsys
     private float[] mRawNits;
@@ -249,6 +253,10 @@
         return mBrightnessRampSlowIncrease;
     }
 
+    SensorIdentifier getAmbientLightSensor() {
+        return mAmbientLightSensor;
+    }
+
     /**
      * @param quirkValue The quirk to test.
      * @return {@code true} if the specified quirk is present in this configuration,
@@ -291,6 +299,7 @@
                 + ", mBrightnessRampFastIncrease=" + mBrightnessRampFastIncrease
                 + ", mBrightnessRampSlowDecrease=" + mBrightnessRampSlowDecrease
                 + ", mBrightnessRampSlowIncrease=" + mBrightnessRampSlowIncrease
+                + ", mAmbientLightSensor=" + mAmbientLightSensor
                 + "}";
         return str;
     }
@@ -318,7 +327,7 @@
 
     private static DisplayDeviceConfig getConfigFromPmValues(Context context) {
         DisplayDeviceConfig config = new DisplayDeviceConfig(context);
-        config.initFromPmValues();
+        config.initFromDefaultValues();
         return config;
     }
 
@@ -342,6 +351,7 @@
                 loadHighBrightnessModeData(config);
                 loadQuirks(config);
                 loadBrightnessRamps(config);
+                loadAmbientLightSensorFromDdc(config);
             } else {
                 Slog.w(TAG, "DisplayDeviceConfig file is null");
             }
@@ -357,9 +367,10 @@
         loadBrightnessConstraintsFromConfigXml();
         loadBrightnessMapFromConfigXml();
         loadBrightnessRampsFromConfigXml();
+        loadAmbientLightSensorFromConfigXml();
     }
 
-    private void initFromPmValues() {
+    private void initFromDefaultValues() {
         // Set all to basic values
         mBacklightMinimum = PowerManager.BRIGHTNESS_MIN;
         mBacklightMaximum = PowerManager.BRIGHTNESS_MAX;
@@ -369,6 +380,7 @@
         mBrightnessRampSlowDecrease = PowerManager.BRIGHTNESS_MAX;
         mBrightnessRampSlowIncrease = PowerManager.BRIGHTNESS_MAX;
         setSimpleMappingStrategyValues();
+        loadAmbientLightSensorFromConfigXml();
     }
 
     private void loadBrightnessDefaultFromDdcXml(DisplayConfiguration config) {
@@ -637,6 +649,33 @@
         mBrightnessRampSlowDecrease = mBrightnessRampSlowIncrease;
     }
 
+    private void loadAmbientLightSensorFromConfigXml() {
+        mAmbientLightSensor.name = "";
+        mAmbientLightSensor.type = mContext.getResources().getString(
+                com.android.internal.R.string.config_displayLightSensorType);
+    }
+
+    private void loadAmbientLightSensorFromDdc(DisplayConfiguration config) {
+        final SensorDetails sensorDetails = config.getLightSensor();
+        if (sensorDetails != null) {
+            mAmbientLightSensor.type = sensorDetails.getType();
+            mAmbientLightSensor.name = sensorDetails.getName();
+        }
+    }
+
+    static class SensorIdentifier {
+        public String type;
+        public String name;
+
+        @Override
+        public String toString() {
+            return "Sensor{"
+                    + "type: \"" + type + "\""
+                    + ", name: \"" + name + "\""
+                    + "} ";
+        }
+    }
+
     /**
      * Container for high brightness mode configuration data.
      */
diff --git a/services/core/java/com/android/server/display/DisplayPowerController.java b/services/core/java/com/android/server/display/DisplayPowerController.java
index 5cd0534..86e4fd0 100644
--- a/services/core/java/com/android/server/display/DisplayPowerController.java
+++ b/services/core/java/com/android/server/display/DisplayPowerController.java
@@ -368,6 +368,8 @@
     // The controller for the automatic brightness level.
     private AutomaticBrightnessController mAutomaticBrightnessController;
 
+    private Sensor mLightSensor;
+
     // The mapper between ambient lux, display backlight values, and display brightness.
     @Nullable
     private BrightnessMappingStrategy mBrightnessMapper;
@@ -418,6 +420,8 @@
     // True if this DisplayPowerController has been stopped and should no longer be running.
     private boolean mStopped;
 
+    private DisplayDeviceConfig mDisplayDeviceConfig;
+
     /**
      * Creates the display power controller.
      */
@@ -478,12 +482,12 @@
                 com.android.internal.R.bool.config_allowAutoBrightnessWhileDozing);
 
 
-        DisplayDeviceConfig displayDeviceConfig = logicalDisplay
+        mDisplayDeviceConfig = logicalDisplay
                 .getPrimaryDisplayDeviceLocked().getDisplayDeviceConfig();
-        mBrightnessRampRateFastDecrease = displayDeviceConfig.getBrightnessRampFastDecrease();
-        mBrightnessRampRateFastIncrease = displayDeviceConfig.getBrightnessRampFastIncrease();
-        mBrightnessRampRateSlowDecrease = displayDeviceConfig.getBrightnessRampSlowDecrease();
-        mBrightnessRampRateSlowIncrease = displayDeviceConfig.getBrightnessRampSlowIncrease();
+        mBrightnessRampRateFastDecrease = mDisplayDeviceConfig.getBrightnessRampFastDecrease();
+        mBrightnessRampRateFastIncrease = mDisplayDeviceConfig.getBrightnessRampFastIncrease();
+        mBrightnessRampRateSlowDecrease = mDisplayDeviceConfig.getBrightnessRampSlowDecrease();
+        mBrightnessRampRateSlowIncrease = mDisplayDeviceConfig.getBrightnessRampSlowIncrease();
         mSkipScreenOnBrightnessRamp = resources.getBoolean(
                 com.android.internal.R.bool.config_skipScreenOnBrightnessRamp);
 
@@ -534,16 +538,12 @@
                         + "config_autoBrightnessLightSensorRate (" + lightSensorRate + ").");
             }
 
-            String lightSensorType = resources.getString(
-                    com.android.internal.R.string.config_displayLightSensorType);
-            Sensor lightSensor = findDisplayLightSensor(lightSensorType);
+            loadAmbientLightSensor();
 
-            final DisplayDeviceConfig ddc =
-                    logicalDisplay.getPrimaryDisplayDeviceLocked().getDisplayDeviceConfig();
-            mBrightnessMapper = BrightnessMappingStrategy.create(resources, ddc);
+            mBrightnessMapper = BrightnessMappingStrategy.create(resources, mDisplayDeviceConfig);
             if (mBrightnessMapper != null) {
                 mAutomaticBrightnessController = new AutomaticBrightnessController(this,
-                        handler.getLooper(), sensorManager, lightSensor, mBrightnessMapper,
+                        handler.getLooper(), sensorManager, mLightSensor, mBrightnessMapper,
                         lightSensorWarmUpTimeConfig, PowerManager.BRIGHTNESS_MIN,
                         PowerManager.BRIGHTNESS_MAX, dozeScaleFactor, lightSensorRate,
                         initialLightSensorRate, brighteningLightDebounce, darkeningLightDebounce,
@@ -597,8 +597,8 @@
         mDisplayWhiteBalanceSettings = displayWhiteBalanceSettings;
         mDisplayWhiteBalanceController = displayWhiteBalanceController;
 
-        if (displayDeviceConfig != null && displayDeviceConfig.getNits() != null) {
-            mNitsRange = displayDeviceConfig.getNits();
+        if (mDisplayDeviceConfig != null && mDisplayDeviceConfig.getNits() != null) {
+            mNitsRange = mDisplayDeviceConfig.getNits();
         } else {
             Slog.w(TAG, "Screen brightness nits configuration is unavailable; falling back");
             mNitsRange = BrightnessMappingStrategy.getFloatArray(context.getResources()
@@ -638,17 +638,19 @@
         mBrightnessMapper.recalculateSplines(mCdsi.isReduceBrightColorsActivated(), adjustedNits);
     }
 
-    private Sensor findDisplayLightSensor(String sensorType) {
-        if (!TextUtils.isEmpty(sensorType)) {
-            List<Sensor> sensors = mSensorManager.getSensorList(Sensor.TYPE_ALL);
-            for (int i = 0; i < sensors.size(); i++) {
-                Sensor sensor = sensors.get(i);
-                if (sensorType.equals(sensor.getStringType())) {
+    private Sensor findSensor(String sensorType, String sensorName, int fallbackType) {
+        final boolean isNameSpecified = !TextUtils.isEmpty(sensorName);
+        final boolean isTypeSpecified = !TextUtils.isEmpty(sensorType);
+        List<Sensor> sensors = mSensorManager.getSensorList(Sensor.TYPE_ALL);
+        if (isNameSpecified || isTypeSpecified) {
+            for (Sensor sensor : sensors) {
+                if ((!isNameSpecified || sensorName.equals(sensor.getName()))
+                        && (!isTypeSpecified || sensorType.equals(sensor.getStringType()))) {
                     return sensor;
                 }
             }
         }
-        return mSensorManager.getDefaultSensor(Sensor.TYPE_LIGHT);
+        return mSensorManager.getDefaultSensor(fallbackType);
     }
 
     /**
@@ -767,6 +769,9 @@
         // TODO: b/175821789 - Support high brightness on multiple (folding) displays
 
         mUniqueDisplayId = mLogicalDisplay.getPrimaryDisplayDeviceLocked().getUniqueId();
+        mDisplayDeviceConfig = mLogicalDisplay.getPrimaryDisplayDeviceLocked()
+                .getDisplayDeviceConfig();
+        loadAmbientLightSensor();
     }
 
     /**
@@ -1510,6 +1515,14 @@
         mReportedScreenStateToPolicy = state;
     }
 
+    private void loadAmbientLightSensor() {
+        DisplayDeviceConfig.SensorIdentifier lightSensor =
+                mDisplayDeviceConfig.getAmbientLightSensor();
+        String lightSensorName = lightSensor.name;
+        String lightSensorType = lightSensor.type;
+        mLightSensor = findSensor(lightSensorType, lightSensorName, Sensor.TYPE_LIGHT);
+    }
+
     private float clampScreenBrightnessForVr(float value) {
         return MathUtils.constrain(
                 value, mScreenBrightnessForVrRangeMinimum,
@@ -1987,6 +2000,7 @@
             pw.println();
             pw.println("Display Power Controller:");
             pw.println("  mDisplayId=" + mDisplayId);
+            pw.println("  mLightSensor=" + mLightSensor);
 
             pw.println();
             pw.println("Display Power Controller Locked State:");
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 e4b9612..01834dd 100644
--- a/services/core/xsd/display-device-config/display-device-config.xsd
+++ b/services/core/xsd/display-device-config/display-device-config.xsd
@@ -48,6 +48,9 @@
                 <xs:element type="nonNegativeDecimal" name="screenBrightnessRampSlowIncrease">
                     <xs:annotation name="final"/>
                 </xs:element>
+                <xs:element type="sensorDetails" name="lightSensor">
+                    <xs:annotation name="final"/>
+                </xs:element>
             </xs:sequence>
         </xs:complexType>
     </xs:element>
@@ -119,4 +122,18 @@
             <xs:minInclusive value="0.0"/>
         </xs:restriction>
     </xs:simpleType>
+
+    <xs:complexType name="sensorDetails">
+        <xs:sequence>
+            <xs:element type="xs:string" name="type" minOccurs="0" maxOccurs="1">
+                <xs:annotation name="nullable" />
+                <xs:annotation name="final"/>
+            </xs:element>
+            <xs:element type="xs:string" name="name" minOccurs="0" maxOccurs="1">
+                <xs:annotation name="nullable" />
+                <xs:annotation name="final"/>
+            </xs:element>
+        </xs:sequence>
+    </xs:complexType>
+
 </xs:schema>
diff --git a/services/core/xsd/display-device-config/schema/current.txt b/services/core/xsd/display-device-config/schema/current.txt
index eb3f1b7..a848f82 100644
--- a/services/core/xsd/display-device-config/schema/current.txt
+++ b/services/core/xsd/display-device-config/schema/current.txt
@@ -4,6 +4,7 @@
   public class DisplayConfiguration {
     ctor public DisplayConfiguration();
     method public com.android.server.display.config.HighBrightnessMode getHighBrightnessMode();
+    method public final com.android.server.display.config.SensorDetails getLightSensor();
     method public com.android.server.display.config.DisplayQuirks getQuirks();
     method @NonNull public final java.math.BigDecimal getScreenBrightnessDefault();
     method @NonNull public final com.android.server.display.config.NitsMap getScreenBrightnessMap();
@@ -12,6 +13,7 @@
     method public final java.math.BigDecimal getScreenBrightnessRampSlowDecrease();
     method public final java.math.BigDecimal getScreenBrightnessRampSlowIncrease();
     method public void setHighBrightnessMode(com.android.server.display.config.HighBrightnessMode);
+    method public final void setLightSensor(com.android.server.display.config.SensorDetails);
     method public void setQuirks(com.android.server.display.config.DisplayQuirks);
     method public final void setScreenBrightnessDefault(@NonNull java.math.BigDecimal);
     method public final void setScreenBrightnessMap(@NonNull com.android.server.display.config.NitsMap);
@@ -61,6 +63,14 @@
     method public final void setValue(@NonNull java.math.BigDecimal);
   }
 
+  public class SensorDetails {
+    ctor public SensorDetails();
+    method @Nullable public final String getName();
+    method @Nullable public final String getType();
+    method public final void setName(@Nullable String);
+    method public final void setType(@Nullable String);
+  }
+
   public class XmlParser {
     ctor public XmlParser();
     method public static com.android.server.display.config.DisplayConfiguration read(java.io.InputStream) throws javax.xml.datatype.DatatypeConfigurationException, java.io.IOException, org.xmlpull.v1.XmlPullParserException;