Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 377f357c authored by Darryl L Johnson's avatar Darryl L Johnson
Browse files

Allow toggling the location that display settings are read from.

DisplayWindowSettingsProvider currently only supports reading display
window settings from a single file location. However, this doesn't
support the use case where a device may want to ship with multiple
vendor display setting experiences and allow switching between them at
runtime.

This updates DisplayWindowSettingsProvider to allow overriding the file
path that's used to read display settings. The default is still to read
from the main settings file stored at /vendor/etc/display_settings.xml
but can be changed by setting the global setting:
DEVELOPMENT_WM_DISPLAY_SETTINGS_PATH.

This also removes the flag DEVELOPMENT_IGNORE_VENDOR_DISPLAY_SETTINGS to
since ignoring vendor display settings entirely is no longer needed.

Test: atest WindowManagerSettingsTests
Test: atest DisplayWindowSettingsProviderTests

Bug: 172342357
Bug: 173540615
Change-Id: I11fd2945a4dacef80e1ab921d585c712f20ae55b
parent c36d7b0f
Loading
Loading
Loading
Loading
+5 −4
Original line number Original line Diff line number Diff line
@@ -9797,12 +9797,13 @@ public final class Settings {
                "use_blast_adapter_sv";
                "use_blast_adapter_sv";
        /**
        /**
         * If {@code true}, vendor provided window manager display settings will be ignored.
         * Path to the WindowManager display settings file. If unset, the default file path will
         * (0 = false, 1 = true)
         * be used.
         *
         * @hide
         * @hide
         */
         */
        public static final String DEVELOPMENT_IGNORE_VENDOR_DISPLAY_SETTINGS =
        public static final String DEVELOPMENT_WM_DISPLAY_SETTINGS_PATH =
                "ignore_vendor_display_settings";
                "wm_display_settings_path";
       /**
       /**
        * Whether user has enabled development settings.
        * Whether user has enabled development settings.
+1 −1
Original line number Original line Diff line number Diff line
@@ -230,7 +230,7 @@ public class SettingsBackupTest {
                    Settings.Global.DEVELOPMENT_RENDER_SHADOWS_IN_COMPOSITOR,
                    Settings.Global.DEVELOPMENT_RENDER_SHADOWS_IN_COMPOSITOR,
                    Settings.Global.DEVELOPMENT_USE_BLAST_ADAPTER_SV,
                    Settings.Global.DEVELOPMENT_USE_BLAST_ADAPTER_SV,
                    Settings.Global.DEVELOPMENT_USE_BLAST_ADAPTER_VR,
                    Settings.Global.DEVELOPMENT_USE_BLAST_ADAPTER_VR,
                    Settings.Global.DEVELOPMENT_IGNORE_VENDOR_DISPLAY_SETTINGS,
                    Settings.Global.DEVELOPMENT_WM_DISPLAY_SETTINGS_PATH,
                    Settings.Global.DEVICE_DEMO_MODE,
                    Settings.Global.DEVICE_DEMO_MODE,
                    Settings.Global.BATTERY_SAVER_ADAPTIVE_CONSTANTS,
                    Settings.Global.BATTERY_SAVER_ADAPTIVE_CONSTANTS,
                    Settings.Global.BATTERY_SAVER_CONSTANTS,
                    Settings.Global.BATTERY_SAVER_CONSTANTS,
+121 −115
Original line number Original line Diff line number Diff line
@@ -16,9 +16,9 @@


package com.android.server.wm;
package com.android.server.wm;


import static android.view.WindowManager.DISPLAY_IME_POLICY_FALLBACK_DISPLAY;
import static android.view.WindowManager.DISPLAY_IME_POLICY_LOCAL;
import static android.view.WindowManager.DISPLAY_IME_POLICY_LOCAL;
import static android.view.WindowManager.REMOVE_CONTENT_MODE_UNDEFINED;
import static android.view.WindowManager.REMOVE_CONTENT_MODE_UNDEFINED;
import static android.view.WindowManager.DISPLAY_IME_POLICY_FALLBACK_DISPLAY;


import static com.android.server.wm.WindowManagerDebugConfig.TAG_WITH_CLASS_NAME;
import static com.android.server.wm.WindowManagerDebugConfig.TAG_WITH_CLASS_NAME;
import static com.android.server.wm.WindowManagerDebugConfig.TAG_WM;
import static com.android.server.wm.WindowManagerDebugConfig.TAG_WM;
@@ -64,7 +64,7 @@ class DisplayWindowSettingsProvider implements SettingsProvider {
            ? "DisplayWindowSettingsProvider" : TAG_WM;
            ? "DisplayWindowSettingsProvider" : TAG_WM;


    private static final String DATA_DISPLAY_SETTINGS_FILE_PATH = "system/display_settings.xml";
    private static final String DATA_DISPLAY_SETTINGS_FILE_PATH = "system/display_settings.xml";
    private static final String VENDOR_DISPLAY_SETTINGS_PATH = "etc/display_settings.xml";
    private static final String VENDOR_DISPLAY_SETTINGS_FILE_PATH = "etc/display_settings.xml";
    private static final String WM_DISPLAY_COMMIT_TAG = "wm-displays";
    private static final String WM_DISPLAY_COMMIT_TAG = "wm-displays";


    private static final int IDENTIFIER_UNIQUE_ID = 0;
    private static final int IDENTIFIER_UNIQUE_ID = 0;
@@ -86,34 +86,8 @@ class DisplayWindowSettingsProvider implements SettingsProvider {
        void finishWrite(OutputStream os, boolean success);
        void finishWrite(OutputStream os, boolean success);
    }
    }


    private final ReadableSettingsStorage mVendorSettingsStorage;
    private ReadableSettings mBaseSettings;
    /**
    private final WritableSettings mOverrideSettings;
     * The preferred type of a display identifier to use when storing and retrieving entries from
     * the base (vendor) settings file.
     *
     * @see #getIdentifier(DisplayInfo, int)
     */
    @DisplayIdentifierType
    private int mVendorIdentifierType;
    private final Map<String, SettingsEntry> mVendorSettings = new HashMap<>();

    private final WritableSettingsStorage mOverrideSettingsStorage;
    /**
     * The preferred type of a display identifier to use when storing and retrieving entries from
     * the data (override) settings file.
     *
     * @see #getIdentifier(DisplayInfo, int)
     */
    @DisplayIdentifierType
    private int mOverrideIdentifierType;
    private final Map<String, SettingsEntry> mOverrideSettings = new HashMap<>();

    /**
     * Enables or disables settings provided from the vendor settings storage.
     *
     * @see #setVendorSettingsIgnored(boolean)
     */
    private boolean mIgnoreVendorSettings = true;


    DisplayWindowSettingsProvider() {
    DisplayWindowSettingsProvider() {
        this(new AtomicFileStorage(getVendorSettingsFile()),
        this(new AtomicFileStorage(getVendorSettingsFile()),
@@ -121,43 +95,48 @@ class DisplayWindowSettingsProvider implements SettingsProvider {
    }
    }


    @VisibleForTesting
    @VisibleForTesting
    DisplayWindowSettingsProvider(@NonNull ReadableSettingsStorage vendorSettingsStorage,
    DisplayWindowSettingsProvider(@NonNull ReadableSettingsStorage baseSettingsStorage,
            @NonNull WritableSettingsStorage overrideSettingsStorage) {
            @NonNull WritableSettingsStorage overrideSettingsStorage) {
        mVendorSettingsStorage = vendorSettingsStorage;
        mBaseSettings = new ReadableSettings(baseSettingsStorage);
        mOverrideSettingsStorage = overrideSettingsStorage;
        mOverrideSettings = new WritableSettings(overrideSettingsStorage);
        readSettings();
    }
    }


    /**
    /**
     * Enables or disables settings provided from the vendor settings storage. If {@code true}, the
     * Overrides the path for the file that should be used to read base settings. If {@code null} is
     * vendor settings will be ignored and only the override settings will be returned from
     * passed the default base settings file path will be used.
     * {@link #getSettings(DisplayInfo)}. If {@code false}, settings returned from
     *
     * {@link #getSettings(DisplayInfo)} will be a merged result of the vendor settings and the
     * @see #VENDOR_DISPLAY_SETTINGS_FILE_PATH
     * override settings.
     */
     */
    void setVendorSettingsIgnored(boolean ignored) {
    void setBaseSettingsFilePath(@Nullable String path) {
        mIgnoreVendorSettings = ignored;
        AtomicFile settingsFile;
        if (path != null) {
            settingsFile = new AtomicFile(new File(path), WM_DISPLAY_COMMIT_TAG);
        } else {
            settingsFile = getVendorSettingsFile();
        }

        setBaseSettingsStorage(new AtomicFileStorage(settingsFile));
    }
    }


    /**
    /**
     * Returns whether or not the vendor settings are being ignored.
     * Overrides the storage that should be used to read base settings.
     *
     *
     * @see #setVendorSettingsIgnored(boolean)
     * @see #setBaseSettingsFilePath(String)
     */
     */
    @VisibleForTesting
    @VisibleForTesting
    boolean getVendorSettingsIgnored() {
    void setBaseSettingsStorage(@NonNull ReadableSettingsStorage baseSettingsStorage) {
        return mIgnoreVendorSettings;
        mBaseSettings = new ReadableSettings(baseSettingsStorage);
    }
    }


    @Override
    @Override
    @NonNull
    @NonNull
    public SettingsEntry getSettings(@NonNull DisplayInfo info) {
    public SettingsEntry getSettings(@NonNull DisplayInfo info) {
        SettingsEntry vendorSettings = getVendorSettingsEntry(info);
        SettingsEntry baseSettings = mBaseSettings.getSettingsEntry(info);
        SettingsEntry overrideSettings = getOrCreateOverrideSettingsEntry(info);
        SettingsEntry overrideSettings = mOverrideSettings.getOrCreateSettingsEntry(info);
        if (vendorSettings == null) {
        if (baseSettings == null) {
            return new SettingsEntry(overrideSettings);
            return new SettingsEntry(overrideSettings);
        } else {
        } else {
            SettingsEntry mergedSettings = new SettingsEntry(vendorSettings);
            SettingsEntry mergedSettings = new SettingsEntry(baseSettings);
            mergedSettings.updateFrom(overrideSettings);
            mergedSettings.updateFrom(overrideSettings);
            return mergedSettings;
            return mergedSettings;
        }
        }
@@ -166,99 +145,126 @@ class DisplayWindowSettingsProvider implements SettingsProvider {
    @Override
    @Override
    @NonNull
    @NonNull
    public SettingsEntry getOverrideSettings(@NonNull DisplayInfo info) {
    public SettingsEntry getOverrideSettings(@NonNull DisplayInfo info) {
        return new SettingsEntry(getOrCreateOverrideSettingsEntry(info));
        return new SettingsEntry(mOverrideSettings.getOrCreateSettingsEntry(info));
    }
    }


    @Override
    @Override
    public void updateOverrideSettings(@NonNull DisplayInfo info,
    public void updateOverrideSettings(@NonNull DisplayInfo info,
            @NonNull SettingsEntry overrides) {
            @NonNull SettingsEntry overrides) {
        final SettingsEntry overrideSettings = getOrCreateOverrideSettingsEntry(info);
        mOverrideSettings.updateSettingsEntry(info, overrides);
        boolean changed = overrideSettings.setTo(overrides);
        if (changed) {
            writeOverrideSettings();
        }
    }
    }


    @Nullable
    /**
    private SettingsEntry getVendorSettingsEntry(DisplayInfo info) {
     * Class that allows reading {@link SettingsEntry entries} from a
        if (mIgnoreVendorSettings) {
     * {@link ReadableSettingsStorage}.
            return null;
     */
    private static class ReadableSettings {
        /**
         * The preferred type of a display identifier to use when storing and retrieving entries
         * from the settings entries.
         *
         * @see #getIdentifier(DisplayInfo)
         */
        @DisplayIdentifierType
        protected int mIdentifierType;
        protected final Map<String, SettingsEntry> mSettings = new HashMap<>();

        ReadableSettings(ReadableSettingsStorage settingsStorage) {
            loadSettings(settingsStorage);
        }
        }


        final String identifier = getIdentifier(info, mVendorIdentifierType);
        @Nullable
        final SettingsEntry getSettingsEntry(DisplayInfo info) {
            final String identifier = getIdentifier(info);
            SettingsEntry settings;
            SettingsEntry settings;
            // Try to get corresponding settings using preferred identifier for the current config.
            // Try to get corresponding settings using preferred identifier for the current config.
        if ((settings = mVendorSettings.get(identifier)) != null) {
            if ((settings = mSettings.get(identifier)) != null) {
                return settings;
                return settings;
            }
            }
            // Else, fall back to the display name.
            // Else, fall back to the display name.
        if ((settings = mVendorSettings.get(info.name)) != null) {
            if ((settings = mSettings.get(info.name)) != null) {
                // Found an entry stored with old identifier.
                // Found an entry stored with old identifier.
            mVendorSettings.remove(info.name);
                mSettings.remove(info.name);
            mVendorSettings.put(identifier, settings);
                mSettings.put(identifier, settings);
                return settings;
                return settings;
            }
            }
            return null;
            return null;
        }
        }


        /** Gets the identifier of choice for the current config. */
        protected final String getIdentifier(DisplayInfo displayInfo) {
            if (mIdentifierType == IDENTIFIER_PORT && displayInfo.address != null) {
                // Config suggests using port as identifier for physical displays.
                if (displayInfo.address instanceof DisplayAddress.Physical) {
                    return "port:" + ((DisplayAddress.Physical) displayInfo.address).getPort();
                }
            }
            return displayInfo.uniqueId;
        }

        private void loadSettings(ReadableSettingsStorage settingsStorage) {
            FileData fileData = readSettings(settingsStorage);
            if (fileData != null) {
                mIdentifierType = fileData.mIdentifierType;
                mSettings.putAll(fileData.mSettings);
            }
        }
    }

    /**
     * Class that allows reading {@link SettingsEntry entries} from, and writing entries to, a
     * {@link WritableSettingsStorage}.
     */
    private static final class WritableSettings extends ReadableSettings {
        private final WritableSettingsStorage mSettingsStorage;

        WritableSettings(WritableSettingsStorage settingsStorage) {
            super(settingsStorage);
            mSettingsStorage = settingsStorage;
        }

        @NonNull
        @NonNull
    private SettingsEntry getOrCreateOverrideSettingsEntry(DisplayInfo info) {
        SettingsEntry getOrCreateSettingsEntry(DisplayInfo info) {
        final String identifier = getIdentifier(info, mOverrideIdentifierType);
            final String identifier = getIdentifier(info);
            SettingsEntry settings;
            SettingsEntry settings;
            // Try to get corresponding settings using preferred identifier for the current config.
            // Try to get corresponding settings using preferred identifier for the current config.
        if ((settings = mOverrideSettings.get(identifier)) != null) {
            if ((settings = mSettings.get(identifier)) != null) {
                return settings;
                return settings;
            }
            }
            // Else, fall back to the display name.
            // Else, fall back to the display name.
        if ((settings = mOverrideSettings.get(info.name)) != null) {
            if ((settings = mSettings.get(info.name)) != null) {
                // Found an entry stored with old identifier.
                // Found an entry stored with old identifier.
            mOverrideSettings.remove(info.name);
                mSettings.remove(info.name);
            mOverrideSettings.put(identifier, settings);
                mSettings.put(identifier, settings);
            writeOverrideSettings();
                writeSettings();
                return settings;
                return settings;
            }
            }


            settings = new SettingsEntry();
            settings = new SettingsEntry();
        mOverrideSettings.put(identifier, settings);
            mSettings.put(identifier, settings);
            return settings;
            return settings;
        }
        }


    private void readSettings() {
        void updateSettingsEntry(DisplayInfo info, SettingsEntry settings) {
        FileData vendorFileData = readSettings(mVendorSettingsStorage);
            final SettingsEntry overrideSettings = getOrCreateSettingsEntry(info);
        if (vendorFileData != null) {
            final boolean changed = overrideSettings.setTo(settings);
            mVendorIdentifierType = vendorFileData.mIdentifierType;
            if (changed) {
            mVendorSettings.putAll(vendorFileData.mSettings);
                writeSettings();
        }

        FileData overrideFileData = readSettings(mOverrideSettingsStorage);
        if (overrideFileData != null) {
            mOverrideIdentifierType = overrideFileData.mIdentifierType;
            mOverrideSettings.putAll(overrideFileData.mSettings);
            }
            }
        }
        }


    private void writeOverrideSettings() {
        private void writeSettings() {
            FileData fileData = new FileData();
            FileData fileData = new FileData();
        fileData.mIdentifierType = mOverrideIdentifierType;
            fileData.mIdentifierType = mIdentifierType;
        fileData.mSettings.putAll(mOverrideSettings);
            fileData.mSettings.putAll(mSettings);
        writeSettings(mOverrideSettingsStorage, fileData);
            DisplayWindowSettingsProvider.writeSettings(mSettingsStorage, fileData);
        }
        }

    /** Gets the identifier of choice for the current config. */
    private static String getIdentifier(DisplayInfo displayInfo, @DisplayIdentifierType int type) {
        if (type == IDENTIFIER_PORT && displayInfo.address != null) {
            // Config suggests using port as identifier for physical displays.
            if (displayInfo.address instanceof DisplayAddress.Physical) {
                return "port:" + ((DisplayAddress.Physical) displayInfo.address).getPort();
            }
        }
        return displayInfo.uniqueId;
    }
    }


    @NonNull
    @NonNull
    private static AtomicFile getVendorSettingsFile() {
    private static AtomicFile getVendorSettingsFile() {
        final File vendorFile = new File(Environment.getVendorDirectory(),
        final File vendorFile = new File(Environment.getVendorDirectory(),
                VENDOR_DISPLAY_SETTINGS_PATH);
                VENDOR_DISPLAY_SETTINGS_FILE_PATH);
        return new AtomicFile(vendorFile, WM_DISPLAY_COMMIT_TAG);
        return new AtomicFile(vendorFile, WM_DISPLAY_COMMIT_TAG);
    }
    }


+15 −13
Original line number Original line Diff line number Diff line
@@ -44,8 +44,8 @@ import static android.provider.Settings.Global.DEVELOPMENT_ENABLE_FREEFORM_WINDO
import static android.provider.Settings.Global.DEVELOPMENT_ENABLE_SIZECOMPAT_FREEFORM;
import static android.provider.Settings.Global.DEVELOPMENT_ENABLE_SIZECOMPAT_FREEFORM;
import static android.provider.Settings.Global.DEVELOPMENT_FORCE_DESKTOP_MODE_ON_EXTERNAL_DISPLAYS;
import static android.provider.Settings.Global.DEVELOPMENT_FORCE_DESKTOP_MODE_ON_EXTERNAL_DISPLAYS;
import static android.provider.Settings.Global.DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES;
import static android.provider.Settings.Global.DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES;
import static android.provider.Settings.Global.DEVELOPMENT_IGNORE_VENDOR_DISPLAY_SETTINGS;
import static android.provider.Settings.Global.DEVELOPMENT_RENDER_SHADOWS_IN_COMPOSITOR;
import static android.provider.Settings.Global.DEVELOPMENT_RENDER_SHADOWS_IN_COMPOSITOR;
import static android.provider.Settings.Global.DEVELOPMENT_WM_DISPLAY_SETTINGS_PATH;
import static android.view.Display.DEFAULT_DISPLAY;
import static android.view.Display.DEFAULT_DISPLAY;
import static android.view.Display.INVALID_DISPLAY;
import static android.view.Display.INVALID_DISPLAY;
import static android.view.WindowManager.DISPLAY_IME_POLICY_FALLBACK_DISPLAY;
import static android.view.WindowManager.DISPLAY_IME_POLICY_FALLBACK_DISPLAY;
@@ -796,8 +796,8 @@ public class WindowManagerService extends IWindowManager.Stub
                DEVELOPMENT_ENABLE_SIZECOMPAT_FREEFORM);
                DEVELOPMENT_ENABLE_SIZECOMPAT_FREEFORM);
        private final Uri mRenderShadowsInCompositorUri = Settings.Global.getUriFor(
        private final Uri mRenderShadowsInCompositorUri = Settings.Global.getUriFor(
                DEVELOPMENT_RENDER_SHADOWS_IN_COMPOSITOR);
                DEVELOPMENT_RENDER_SHADOWS_IN_COMPOSITOR);
        private final Uri mIgnoreVendorDisplaySettingsUri = Settings.Global.getUriFor(
        private final Uri mDisplaySettingsPathUri = Settings.Global.getUriFor(
                DEVELOPMENT_IGNORE_VENDOR_DISPLAY_SETTINGS);
                DEVELOPMENT_WM_DISPLAY_SETTINGS_PATH);


        public SettingsObserver() {
        public SettingsObserver() {
            super(new Handler());
            super(new Handler());
@@ -822,7 +822,7 @@ public class WindowManagerService extends IWindowManager.Stub
                    UserHandle.USER_ALL);
                    UserHandle.USER_ALL);
            resolver.registerContentObserver(mRenderShadowsInCompositorUri, false, this,
            resolver.registerContentObserver(mRenderShadowsInCompositorUri, false, this,
                    UserHandle.USER_ALL);
                    UserHandle.USER_ALL);
            resolver.registerContentObserver(mIgnoreVendorDisplaySettingsUri, false, this,
            resolver.registerContentObserver(mDisplaySettingsPathUri, false, this,
                    UserHandle.USER_ALL);
                    UserHandle.USER_ALL);
        }
        }


@@ -867,8 +867,8 @@ public class WindowManagerService extends IWindowManager.Stub
                return;
                return;
            }
            }


            if (mIgnoreVendorDisplaySettingsUri.equals(uri)) {
            if (mDisplaySettingsPathUri.equals(uri)) {
                updateIgnoreVendorDisplaySettings();
                updateDisplaySettingsLocation();
                return;
                return;
            }
            }


@@ -962,12 +962,12 @@ public class WindowManagerService extends IWindowManager.Stub
            mAtmService.mSizeCompatFreeform = sizeCompatFreeform;
            mAtmService.mSizeCompatFreeform = sizeCompatFreeform;
        }
        }


        void updateIgnoreVendorDisplaySettings() {
        void updateDisplaySettingsLocation() {
            final ContentResolver resolver = mContext.getContentResolver();
            final ContentResolver resolver = mContext.getContentResolver();
            final boolean ignoreVendorSettings = Settings.Global.getInt(resolver,
            final String filePath = Settings.Global.getString(resolver,
                    DEVELOPMENT_IGNORE_VENDOR_DISPLAY_SETTINGS, 0) != 0;
                    DEVELOPMENT_WM_DISPLAY_SETTINGS_PATH);
            synchronized (mGlobalLock) {
            synchronized (mGlobalLock) {
                mDisplayWindowSettingsProvider.setVendorSettingsIgnored(ignoreVendorSettings);
                mDisplayWindowSettingsProvider.setBaseSettingsFilePath(filePath);
                mRoot.forAllDisplays(display -> {
                mRoot.forAllDisplays(display -> {
                    mDisplayWindowSettings.applySettingsToDisplayLocked(display);
                    mDisplayWindowSettings.applySettingsToDisplayLocked(display);
                    display.reconfigureDisplayLocked();
                    display.reconfigureDisplayLocked();
@@ -1330,10 +1330,12 @@ public class WindowManagerService extends IWindowManager.Stub
        mForceDesktopModeOnExternalDisplays = Settings.Global.getInt(resolver,
        mForceDesktopModeOnExternalDisplays = Settings.Global.getInt(resolver,
                DEVELOPMENT_FORCE_DESKTOP_MODE_ON_EXTERNAL_DISPLAYS, 0) != 0;
                DEVELOPMENT_FORCE_DESKTOP_MODE_ON_EXTERNAL_DISPLAYS, 0) != 0;


        final boolean ignoreVendorDisplaySettings = Settings.Global.getInt(resolver,
        final String displaySettingsPath = Settings.Global.getString(resolver,
                DEVELOPMENT_IGNORE_VENDOR_DISPLAY_SETTINGS, 0) != 0;
                DEVELOPMENT_WM_DISPLAY_SETTINGS_PATH);
        mDisplayWindowSettingsProvider = new DisplayWindowSettingsProvider();
        mDisplayWindowSettingsProvider = new DisplayWindowSettingsProvider();
        mDisplayWindowSettingsProvider.setVendorSettingsIgnored(ignoreVendorDisplaySettings);
        if (displaySettingsPath != null) {
            mDisplayWindowSettingsProvider.setBaseSettingsFilePath(displaySettingsPath);
        }
        mDisplayWindowSettings = new DisplayWindowSettings(this, mDisplayWindowSettingsProvider);
        mDisplayWindowSettings = new DisplayWindowSettings(this, mDisplayWindowSettingsProvider);


        IntentFilter filter = new IntentFilter();
        IntentFilter filter = new IntentFilter();
+72 −7
Original line number Original line Diff line number Diff line
@@ -16,7 +16,9 @@


package com.android.server.wm;
package com.android.server.wm;


import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN;
import static android.app.WindowConfiguration.WINDOWING_MODE_PINNED;
import static android.app.WindowConfiguration.WINDOWING_MODE_PINNED;
import static android.app.WindowConfiguration.WINDOWING_MODE_UNDEFINED;
import static android.view.WindowManager.DISPLAY_IME_POLICY_LOCAL;
import static android.view.WindowManager.DISPLAY_IME_POLICY_LOCAL;


import static androidx.test.platform.app.InstrumentationRegistry.getInstrumentation;
import static androidx.test.platform.app.InstrumentationRegistry.getInstrumentation;
@@ -28,7 +30,6 @@ import static org.junit.Assert.assertTrue;
import android.annotation.Nullable;
import android.annotation.Nullable;
import android.platform.test.annotations.Presubmit;
import android.platform.test.annotations.Presubmit;
import android.util.TypedXmlPullParser;
import android.util.TypedXmlPullParser;
import android.util.TypedXmlSerializer;
import android.util.Xml;
import android.util.Xml;
import android.view.Display;
import android.view.Display;
import android.view.DisplayAddress;
import android.view.DisplayAddress;
@@ -69,7 +70,8 @@ public class DisplayWindowSettingsProviderTests extends WindowTestsBase {


    private static final File TEST_FOLDER = getInstrumentation().getTargetContext().getCacheDir();
    private static final File TEST_FOLDER = getInstrumentation().getTargetContext().getCacheDir();


    private TestStorage mBaseSettingsStorage;
    private TestStorage mDefaultVendorSettingsStorage;
    private TestStorage mSecondaryVendorSettingsStorage;
    private TestStorage mOverrideSettingsStorage;
    private TestStorage mOverrideSettingsStorage;


    private DisplayContent mPrimaryDisplay;
    private DisplayContent mPrimaryDisplay;
@@ -79,7 +81,8 @@ public class DisplayWindowSettingsProviderTests extends WindowTestsBase {
    public void setUp() throws Exception {
    public void setUp() throws Exception {
        deleteRecursively(TEST_FOLDER);
        deleteRecursively(TEST_FOLDER);


        mBaseSettingsStorage = new TestStorage();
        mDefaultVendorSettingsStorage = new TestStorage();
        mSecondaryVendorSettingsStorage = new TestStorage();
        mOverrideSettingsStorage = new TestStorage();
        mOverrideSettingsStorage = new TestStorage();


        mPrimaryDisplay = mWm.getDefaultDisplayContentLocked();
        mPrimaryDisplay = mWm.getDefaultDisplayContentLocked();
@@ -122,7 +125,7 @@ public class DisplayWindowSettingsProviderTests extends WindowTestsBase {


        // Update settings with new value, should trigger write to injector.
        // Update settings with new value, should trigger write to injector.
        DisplayWindowSettingsProvider provider = new DisplayWindowSettingsProvider(
        DisplayWindowSettingsProvider provider = new DisplayWindowSettingsProvider(
                mBaseSettingsStorage, mOverrideSettingsStorage);
                mDefaultVendorSettingsStorage, mOverrideSettingsStorage);
        SettingsEntry overrideSettings = provider.getOverrideSettings(mPrimaryDisplayInfo);
        SettingsEntry overrideSettings = provider.getOverrideSettings(mPrimaryDisplayInfo);
        overrideSettings.mForcedDensity = 200;
        overrideSettings.mForcedDensity = 200;
        provider.updateOverrideSettings(mPrimaryDisplayInfo, overrideSettings);
        provider.updateOverrideSettings(mPrimaryDisplayInfo, overrideSettings);
@@ -161,13 +164,56 @@ public class DisplayWindowSettingsProviderTests extends WindowTestsBase {
        readAndAssertExpectedSettings(mPrimaryDisplay, expectedSettings);
        readAndAssertExpectedSettings(mPrimaryDisplay, expectedSettings);
    }
    }


    @Test
    public void testReadingDisplaySettingsFromStorage_secondayVendorDisplaySettingsLocation() {
        final String displayIdentifier = mSecondaryDisplay.getDisplayInfo().uniqueId;
        prepareSecondaryDisplaySettings(displayIdentifier);

        final DisplayWindowSettingsProvider provider =
                new DisplayWindowSettingsProvider(mDefaultVendorSettingsStorage,
                        mOverrideSettingsStorage);

        // Expected settings should be empty because the default is to read from the primary vendor
        // settings location.
        SettingsEntry expectedSettings = new SettingsEntry();
        assertEquals(expectedSettings, provider.getSettings(mPrimaryDisplay.getDisplayInfo()));

        // Now switch to secondary vendor settings and assert proper settings.
        provider.setBaseSettingsStorage(mSecondaryVendorSettingsStorage);
        expectedSettings.mWindowingMode = WINDOWING_MODE_FULLSCREEN;
        assertEquals(expectedSettings, provider.getSettings(mPrimaryDisplay.getDisplayInfo()));

        // Switch back to primary and assert settings are empty again.
        provider.setBaseSettingsStorage(mDefaultVendorSettingsStorage);
        expectedSettings.mWindowingMode = WINDOWING_MODE_UNDEFINED;
        assertEquals(expectedSettings, provider.getSettings(mPrimaryDisplay.getDisplayInfo()));
    }

    @Test
    public void testReadingDisplaySettingsFromStorage_overrideSettingsTakePrecedenceOverVendor() {
        final String displayIdentifier = mSecondaryDisplay.getDisplayInfo().uniqueId;
        prepareOverrideDisplaySettings(displayIdentifier);
        prepareSecondaryDisplaySettings(displayIdentifier);

        final DisplayWindowSettingsProvider provider =
                new DisplayWindowSettingsProvider(mDefaultVendorSettingsStorage,
                        mOverrideSettingsStorage);
        provider.setBaseSettingsStorage(mSecondaryVendorSettingsStorage);

        // The windowing mode should be set to WINDOWING_MODE_PINNED because the override settings
        // take precedence over the vendor provided settings.
        SettingsEntry expectedSettings = new SettingsEntry();
        expectedSettings.mWindowingMode = WINDOWING_MODE_PINNED;
        assertEquals(expectedSettings, provider.getSettings(mPrimaryDisplay.getDisplayInfo()));
    }

    @Test
    @Test
    public void testWritingDisplaySettingsToStorage() throws Exception {
    public void testWritingDisplaySettingsToStorage() throws Exception {
        final DisplayInfo secondaryDisplayInfo = mSecondaryDisplay.getDisplayInfo();
        final DisplayInfo secondaryDisplayInfo = mSecondaryDisplay.getDisplayInfo();


        // Write some settings to storage.
        // Write some settings to storage.
        DisplayWindowSettingsProvider provider = new DisplayWindowSettingsProvider(
        DisplayWindowSettingsProvider provider = new DisplayWindowSettingsProvider(
                mBaseSettingsStorage, mOverrideSettingsStorage);
                mDefaultVendorSettingsStorage, mOverrideSettingsStorage);
        SettingsEntry overrideSettings = provider.getOverrideSettings(secondaryDisplayInfo);
        SettingsEntry overrideSettings = provider.getOverrideSettings(secondaryDisplayInfo);
        overrideSettings.mShouldShowSystemDecors = true;
        overrideSettings.mShouldShowSystemDecors = true;
        overrideSettings.mImePolicy = DISPLAY_IME_POLICY_LOCAL;
        overrideSettings.mImePolicy = DISPLAY_IME_POLICY_LOCAL;
@@ -195,7 +241,7 @@ public class DisplayWindowSettingsProviderTests extends WindowTestsBase {


        // Write some settings to storage.
        // Write some settings to storage.
        DisplayWindowSettingsProvider provider = new DisplayWindowSettingsProvider(
        DisplayWindowSettingsProvider provider = new DisplayWindowSettingsProvider(
                mBaseSettingsStorage, mOverrideSettingsStorage);
                mDefaultVendorSettingsStorage, mOverrideSettingsStorage);
        SettingsEntry overrideSettings = provider.getOverrideSettings(secondaryDisplayInfo);
        SettingsEntry overrideSettings = provider.getOverrideSettings(secondaryDisplayInfo);
        overrideSettings.mShouldShowSystemDecors = true;
        overrideSettings.mShouldShowSystemDecors = true;
        overrideSettings.mImePolicy = DISPLAY_IME_POLICY_LOCAL;
        overrideSettings.mImePolicy = DISPLAY_IME_POLICY_LOCAL;
@@ -236,10 +282,29 @@ public class DisplayWindowSettingsProviderTests extends WindowTestsBase {
        mOverrideSettingsStorage.setReadStream(is);
        mOverrideSettingsStorage.setReadStream(is);
    }
    }


    /**
     * Prepares display settings and stores in {@link #mSecondaryVendorSettingsStorage}. Uses
     * provided display identifier and stores windowingMode=WINDOWING_MODE_FULLSCREEN.
     */
    private void prepareSecondaryDisplaySettings(String displayIdentifier) {
        String contents = "<?xml version='1.0' encoding='utf-8' standalone='yes' ?>\n"
                + "<display-settings>\n";
        if (displayIdentifier != null) {
            contents += "  <display\n"
                    + "    name=\"" + displayIdentifier + "\"\n"
                    + "    windowingMode=\"" + WINDOWING_MODE_FULLSCREEN + "\"/>\n";
        }
        contents += "</display-settings>\n";

        final InputStream is = new ByteArrayInputStream(contents.getBytes(StandardCharsets.UTF_8));
        mSecondaryVendorSettingsStorage.setReadStream(is);
    }

    private void readAndAssertExpectedSettings(DisplayContent displayContent,
    private void readAndAssertExpectedSettings(DisplayContent displayContent,
            SettingsEntry expectedSettings) {
            SettingsEntry expectedSettings) {
        final DisplayWindowSettingsProvider provider =
        final DisplayWindowSettingsProvider provider =
                new DisplayWindowSettingsProvider(mBaseSettingsStorage, mOverrideSettingsStorage);
                new DisplayWindowSettingsProvider(mDefaultVendorSettingsStorage,
                        mOverrideSettingsStorage);
        assertEquals(expectedSettings, provider.getSettings(displayContent.getDisplayInfo()));
        assertEquals(expectedSettings, provider.getSettings(displayContent.getDisplayInfo()));
    }
    }


Loading