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

Commit 33ce8f47 authored by Robert Snoeberger's avatar Robert Snoeberger Committed by Android (Google) Code Review
Browse files

Merge "Implemented the mechanism of hiding clock face based on phenotype flag." into qt-r1-dev

parents 41a4236e f443938d
Loading
Loading
Loading
Loading
+7 −0
Original line number Diff line number Diff line
@@ -132,6 +132,13 @@ public final class SystemUiDeviceConfigFlags {
     */
    public static final String ASSIST_HANDLES_SHOWN_FREQUENCY_THRESHOLD_MS =
            "assist_handles_shown_frequency_threshold_ms";
    // Flag related to clock face

    /**
     * (String) Contains the clock plugin service names that are not allow to be shown.
     * Each service name is seperated by a comma(",") in the string.
     */
    public static final String CLOCK_FACE_BLACKLIST = "clock_face_blacklist";

    /**
     * (long) How long, in milliseconds, for teaching behaviors to wait before considering the user
+64 −16
Original line number Diff line number Diff line
@@ -15,6 +15,8 @@
 */
package com.android.keyguard.clock;

import static com.android.internal.config.sysui.SystemUiDeviceConfigFlags.CLOCK_FACE_BLACKLIST;

import android.annotation.Nullable;
import android.content.ContentResolver;
import android.content.Context;
@@ -24,9 +26,12 @@ import android.net.Uri;
import android.os.Handler;
import android.os.Looper;
import android.os.UserHandle;
import android.provider.DeviceConfig;
import android.provider.Settings;
import android.util.ArrayMap;
import android.util.ArraySet;
import android.util.DisplayMetrics;
import android.util.Log;
import android.view.LayoutInflater;

import androidx.annotation.VisibleForTesting;
@@ -42,10 +47,12 @@ import com.android.systemui.shared.plugins.PluginManager;
import com.android.systemui.util.InjectionInflationController;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.function.Supplier;
import java.util.stream.Collectors;

import javax.inject.Inject;
import javax.inject.Singleton;
@@ -67,6 +74,8 @@ public final class ClockManager {
    private final Handler mMainHandler = new Handler(Looper.getMainLooper());
    private final CurrentUserObservable mCurrentUserObservable;

    private final ArraySet<String> mBlacklistedClockPlugins = new ArraySet<>();

    /**
     * Observe settings changes to know when to switch the clock face.
     */
@@ -155,6 +164,41 @@ public final class ClockManager {
        DisplayMetrics dm = res.getDisplayMetrics();
        mWidth = dm.widthPixels;
        mHeight = dm.heightPixels;

        updateBlackList();
        registerDeviceConfigListener();
    }

    private void updateBlackList() {
        String blacklist = getBlackListFromConfig();

        mBlacklistedClockPlugins.clear();
        if (blacklist != null && !blacklist.isEmpty()) {
            mBlacklistedClockPlugins.addAll(Arrays.asList(blacklist.split(",")));
        }
    }

    String getBlackListFromConfig() {
        return DeviceConfig.getString(
            DeviceConfig.NAMESPACE_SYSTEMUI, CLOCK_FACE_BLACKLIST, null);
    }

    private void registerDeviceConfigListener() {
        DeviceConfig.addOnPropertiesChangedListener(
                DeviceConfig.NAMESPACE_SYSTEMUI,
                r -> mMainHandler.post(r),
                properties -> onDeviceConfigPropertiesChanged(properties.getNamespace()));
    }

    void onDeviceConfigPropertiesChanged(String namespace) {
        if (!DeviceConfig.NAMESPACE_SYSTEMUI.equals(namespace)) {
            Log.e(TAG, "Received update from DeviceConfig for unrelated namespace: "
                    + namespace);
            return;
        }

        updateBlackList();
        reload();
    }

    /**
@@ -240,9 +284,9 @@ public final class ClockManager {
    }

    private void reload() {
        mPreviewClocks.reload();
        mPreviewClocks.reloadCurrentClock();
        mListeners.forEach((listener, clocks) -> {
            clocks.reload();
            clocks.reloadCurrentClock();
            ClockPlugin clock = clocks.getCurrentClock();
            if (clock instanceof DefaultClockController) {
                listener.onClockChanged(null);
@@ -287,20 +331,13 @@ public final class ClockManager {
        @Override
        public void onPluginConnected(ClockPlugin plugin, Context pluginContext) {
            addClockPlugin(plugin);
            reload();
            if (plugin == mCurrentClock) {
                ClockManager.this.reload();
            }
            reloadIfNeeded(plugin);
        }

        @Override
        public void onPluginDisconnected(ClockPlugin plugin) {
            boolean isCurrentClock = plugin == mCurrentClock;
            removeClockPlugin(plugin);
            reload();
            if (isCurrentClock) {
                ClockManager.this.reload();
            }
            reloadIfNeeded(plugin);
        }

        /**
@@ -313,10 +350,12 @@ public final class ClockManager {
        }

        /**
         * Get information about available clock faces.
         * Get information about clock faces which are available and not in blacklist.
         */
        List<ClockInfo> getInfo() {
            return mClockInfo;
            return mClockInfo.stream()
                .filter(info -> !mBlacklistedClockPlugins.contains(info.getId()))
                .collect(Collectors.toList());
        }

        /**
@@ -347,10 +386,19 @@ public final class ClockManager {
            }
        }

        private void reloadIfNeeded(ClockPlugin plugin) {
            final boolean wasCurrentClock = plugin == mCurrentClock;
            reloadCurrentClock();
            final boolean isCurrentClock = plugin == mCurrentClock;
            if (wasCurrentClock || isCurrentClock) {
                ClockManager.this.reload();
            }
        }

        /**
         * Update the current clock.
         */
        void reload() {
        void reloadCurrentClock() {
            mCurrentClock = getClockPlugin();
        }

@@ -359,7 +407,7 @@ public final class ClockManager {
            if (ClockManager.this.isDocked()) {
                final String name = mSettingsWrapper.getDockedClockFace(
                        mCurrentUserObservable.getCurrentUser().getValue());
                if (name != null) {
                if (name != null && !mBlacklistedClockPlugins.contains(name)) {
                    plugin = mClocks.get(name);
                    if (plugin != null) {
                        return plugin;
@@ -368,7 +416,7 @@ public final class ClockManager {
            }
            final String name = mSettingsWrapper.getLockScreenCustomClockFace(
                    mCurrentUserObservable.getCurrentUser().getValue());
            if (name != null) {
            if (name != null && !mBlacklistedClockPlugins.contains(name)) {
                plugin = mClocks.get(name);
            }
            return plugin;
+32 −1
Original line number Diff line number Diff line
@@ -20,12 +20,14 @@ import static com.google.common.truth.Truth.assertThat;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.anyInt;
import static org.mockito.Mockito.reset;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;

import android.content.ContentResolver;
import android.database.ContentObserver;
import android.net.Uri;
import android.provider.DeviceConfig;
import android.test.suitebuilder.annotation.SmallTest;
import android.testing.AndroidTestingRunner;
import android.testing.TestableLooper.RunWithLooper;
@@ -50,6 +52,8 @@ import org.mockito.ArgumentCaptor;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;

import java.util.List;

@SmallTest
@RunWith(AndroidTestingRunner.class)
// Need to run tests on main looper because LiveData operations such as setData, observe,
@@ -63,7 +67,7 @@ public final class ClockManagerTest extends SysuiTestCase {
    private static final int SECONDARY_USER_ID = 11;
    private static final Uri SETTINGS_URI = null;

    private ClockManager mClockManager;
    ClockManager mClockManager;
    private ContentObserver mContentObserver;
    private DockManagerFake mFakeDockManager;
    private MutableLiveData<Integer> mCurrentUser;
@@ -139,6 +143,33 @@ public final class ClockManagerTest extends SysuiTestCase {
        assertThat(mClockManager.getCurrentClock()).isInstanceOf(BUBBLE_CLOCK_CLASS);
    }

    @Test
    public void getCurrentClock_inBlackList() {
        mClockManager = spy(mClockManager);
        // GIVEN that settings is set to the bubble clock face
        when(mMockSettingsWrapper.getLockScreenCustomClockFace(anyInt())).thenReturn(BUBBLE_CLOCK);
        // WHEN settings change event is fired
        mContentObserver.onChange(false, SETTINGS_URI, MAIN_USER_ID);
        // GIVEN that bubble clock is in blacklist
        when(mClockManager.getBlackListFromConfig()).thenReturn(BUBBLE_CLOCK);
        // WHEN device config change of systemui is fired
        mClockManager.onDeviceConfigPropertiesChanged(DeviceConfig.NAMESPACE_SYSTEMUI);
        // THEN the result is null, indicated the current clock should be reset to the default one.
        assertThat(mClockManager.getCurrentClock()).isNull();
    }

    @Test
    public void getClockInfo_inBlackList() {
        mClockManager = spy(mClockManager);
        // GIVEN that bubble clock is in blacklist
        when(mClockManager.getBlackListFromConfig()).thenReturn(BUBBLE_CLOCK);
        // WHEN device config change of systemui is fired
        mClockManager.onDeviceConfigPropertiesChanged(DeviceConfig.NAMESPACE_SYSTEMUI);
        // THEN the ClockInfo should not contain bubble clock
        List<ClockInfo> clocks = mClockManager.getClockInfos();
        assertThat(clocks.stream().anyMatch(info -> BUBBLE_CLOCK.equals(info.getId()))).isFalse();
    }

    @Test
    public void onClockChanged_customClock() {
        // GIVEN that settings is set to the bubble clock face