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

Commit 91f0e463 authored by Bill Lin's avatar Bill Lin
Browse files

Refactor OneHanded mode UiEventLogger implementation

1) Move UiEventLogger from static to non-static
2) Rename to OneHandedUiEventLogger to align wm-shell components
3) Remove unused code from OneHandedUiEventLogger
4) Refine the call of stopOneHandedWithUiEvent()
5) Only register TaskStackListenerCallback when enabled
6) Override getId() in the enum to ensure UiEventLoggerImpl
   can obtain the event corresponding id accordingly

Fixes: 176513465
Test: adb shell cmd stats print-logs
Test: manual + statsd_testdrive -terse 90
Test: atest WMShellUnitTests
Change-Id: Ic2fb1a2bbf87e647b0883d50b64ced53aa37d613
parent 81895251
Loading
Loading
Loading
Loading
+2 −2
Original line number Diff line number Diff line
@@ -49,9 +49,9 @@ public interface OneHanded {
    void stopOneHanded();

    /**
     * Exits one handed mode with {@link OneHandedEvents}.
     * Exits one handed mode with {@link OneHandedUiEventLogger}.
     */
    void stopOneHanded(int event);
    void stopOneHanded(int uiEvent);

    /**
     * Set navigation 3 button mode enabled or disabled by users.
+54 −45
Original line number Diff line number Diff line
@@ -37,6 +37,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.annotation.VisibleForTesting;

import com.android.internal.logging.UiEventLogger;
import com.android.wm.shell.R;
import com.android.wm.shell.common.DisplayChangeController;
import com.android.wm.shell.common.DisplayController;
@@ -47,7 +48,6 @@ import com.android.wm.shell.common.annotations.ExternalThread;
import com.android.wm.shell.onehanded.OneHandedGestureHandler.OneHandedGestureEventCallback;

import java.io.PrintWriter;
import java.util.concurrent.Executor;

/**
 * Manages and manipulates the one handed states, transitions, and gesture for phones.
@@ -73,6 +73,8 @@ public class OneHandedController {
    private final OneHandedTimeoutHandler mTimeoutHandler;
    private final OneHandedTouchHandler mTouchHandler;
    private final OneHandedTutorialHandler mTutorialHandler;
    private final OneHandedUiEventLogger mOneHandedUiEventLogger;
    private final TaskStackListenerImpl mTaskStackListener;
    private final IOverlayManager mOverlayManager;
    private final ShellExecutor mMainExecutor;
    private final Handler mMainHandler;
@@ -117,15 +119,28 @@ public class OneHandedController {
                }
            };

    private final TaskStackListenerCallback mTaskStackListenerCallback =
            new TaskStackListenerCallback() {
                @Override
                public void onTaskCreated(int taskId, ComponentName componentName) {
                    stopOneHanded(OneHandedUiEventLogger.EVENT_ONE_HANDED_TRIGGER_APP_TAPS_OUT);
                }

                @Override
                public void onTaskMovedToFront(int taskId) {
                    stopOneHanded(OneHandedUiEventLogger.EVENT_ONE_HANDED_TRIGGER_APP_TAPS_OUT);
                }
            };


    /**
     * Creates {@link OneHanded}, returns {@code null} if the feature is not supported.
     */
    @Nullable
    public static OneHanded create(
            Context context, DisplayController displayController,
            TaskStackListenerImpl taskStackListener,
            ShellExecutor mainExecutor,
            Handler mainHandler) {
            TaskStackListenerImpl taskStackListener, UiEventLogger uiEventLogger,
            ShellExecutor mainExecutor, Handler mainHandler) {
        if (!SystemProperties.getBoolean(SUPPORT_ONE_HANDED_MODE, false)) {
            Slog.w(TAG, "Device doesn't support OneHanded feature");
            return null;
@@ -145,12 +160,13 @@ public class OneHandedController {
        OneHandedDisplayAreaOrganizer organizer = new OneHandedDisplayAreaOrganizer(
                context, displayController, animationController, tutorialHandler,
                oneHandedBackgroundPanelOrganizer, mainExecutor);
        OneHandedUiEventLogger oneHandedUiEventsLogger = new OneHandedUiEventLogger(uiEventLogger);
        IOverlayManager overlayManager = IOverlayManager.Stub.asInterface(
                ServiceManager.getService(Context.OVERLAY_SERVICE));
        return new OneHandedController(context, displayController,
                oneHandedBackgroundPanelOrganizer, organizer, touchHandler, tutorialHandler,
                gestureHandler, timeoutHandler, overlayManager, taskStackListener, mainExecutor,
                mainHandler).mImpl;
                gestureHandler, timeoutHandler, oneHandedUiEventsLogger, overlayManager,
                taskStackListener, mainExecutor, mainHandler).mImpl;
    }

    @VisibleForTesting
@@ -162,6 +178,7 @@ public class OneHandedController {
            OneHandedTutorialHandler tutorialHandler,
            OneHandedGestureHandler gestureHandler,
            OneHandedTimeoutHandler timeoutHandler,
            OneHandedUiEventLogger uiEventsLogger,
            IOverlayManager overlayManager,
            TaskStackListenerImpl taskStackListener,
            ShellExecutor mainExecutor,
@@ -176,6 +193,8 @@ public class OneHandedController {
        mOverlayManager = overlayManager;
        mMainExecutor = mainExecutor;
        mMainHandler = mainHandler;
        mOneHandedUiEventLogger = uiEventsLogger;
        mTaskStackListener = taskStackListener;

        final float offsetPercentageConfig = context.getResources().getFraction(
                R.fraction.config_one_handed_offset, 1, 1);
@@ -203,19 +222,6 @@ public class OneHandedController {
        setupGesturalOverlay();
        updateSettings();

        taskStackListener.addListener(
                new TaskStackListenerCallback() {
                    @Override
                    public void onTaskCreated(int taskId, ComponentName componentName) {
                        stopOneHanded(OneHandedEvents.EVENT_ONE_HANDED_TRIGGER_APP_TAPS_OUT);
                    }

                    @Override
                    public void onTaskMovedToFront(int taskId) {
                        stopOneHanded(OneHandedEvents.EVENT_ONE_HANDED_TRIGGER_APP_TAPS_OUT);
                    }
                });

        mAccessibilityManager = (AccessibilityManager)
                context.getSystemService(Context.ACCESSIBILITY_SERVICE);
        mAccessibilityManager.addAccessibilityStateChangeListener(
@@ -234,6 +240,11 @@ public class OneHandedController {
     * Set one handed enabled or disabled by when user update settings
     */
    void setTaskChangeToExit(boolean enabled) {
        if (enabled) {
            mTaskStackListener.addListener(mTaskStackListenerCallback);
        } else {
            mTaskStackListener.removeListener(mTaskStackListenerCallback);
        }
        mTaskChangeToExit = enabled;
    }

@@ -252,7 +263,8 @@ public class OneHandedController {
            mDisplayAreaOrganizer.scheduleOffset(0, yOffSet);
            mTimeoutHandler.resetTimer();

            OneHandedEvents.writeEvent(OneHandedEvents.EVENT_ONE_HANDED_TRIGGER_GESTURE_IN);
            mOneHandedUiEventLogger.writeEvent(
                    OneHandedUiEventLogger.EVENT_ONE_HANDED_TRIGGER_GESTURE_IN);
        }
    }

@@ -264,17 +276,12 @@ public class OneHandedController {
        }
    }

    private void stopOneHanded(int event) {
        if (!mTaskChangeToExit && event == OneHandedEvents.EVENT_ONE_HANDED_TRIGGER_APP_TAPS_OUT) {
            //Task change exit not enable, do nothing and return here.
            return;
        }

    private void stopOneHanded(int uiEvent) {
        if (mDisplayAreaOrganizer.isInOneHanded()) {
            OneHandedEvents.writeEvent(event);
            mDisplayAreaOrganizer.scheduleOffset(0, 0);
            mTimeoutHandler.removeTimer();
            mOneHandedUiEventLogger.writeEvent(uiEvent);
        }

        stopOneHanded();
    }

    private void setThreeButtonModeEnabled(boolean enabled) {
@@ -292,11 +299,14 @@ public class OneHandedController {

    private void setupCallback() {
        mTouchHandler.registerTouchEventListener(() ->
                stopOneHanded(OneHandedEvents.EVENT_ONE_HANDED_TRIGGER_OVERSPACE_OUT));
                stopOneHanded(OneHandedUiEventLogger.EVENT_ONE_HANDED_TRIGGER_OVERSPACE_OUT));
        mDisplayAreaOrganizer.registerTransitionCallback(mTouchHandler);
        mDisplayAreaOrganizer.registerTransitionCallback(mGestureHandler);
        mDisplayAreaOrganizer.registerTransitionCallback(mTutorialHandler);
        mDisplayAreaOrganizer.registerTransitionCallback(mBackgroundPanelOrganizer);
        if (mTaskChangeToExit) {
            mTaskStackListener.addListener(mTaskStackListenerCallback);
        }
    }

    private void setupSettingObservers() {
@@ -334,9 +344,9 @@ public class OneHandedController {
    private void onEnabledSettingChanged() {
        final boolean enabled = OneHandedSettingsUtil.getSettingsOneHandedModeEnabled(
                mContext.getContentResolver());
        OneHandedEvents.writeEvent(enabled
                ? OneHandedEvents.EVENT_ONE_HANDED_SETTINGS_ENABLED_ON
                : OneHandedEvents.EVENT_ONE_HANDED_SETTINGS_ENABLED_OFF);
        mOneHandedUiEventLogger.writeEvent(enabled
                ? OneHandedUiEventLogger.EVENT_ONE_HANDED_SETTINGS_ENABLED_ON
                : OneHandedUiEventLogger.EVENT_ONE_HANDED_SETTINGS_ENABLED_OFF);

        setOneHandedEnabled(enabled);

@@ -349,25 +359,25 @@ public class OneHandedController {
    private void onTimeoutSettingChanged() {
        final int newTimeout = OneHandedSettingsUtil.getSettingsOneHandedModeTimeout(
                mContext.getContentResolver());
        int metricsId = OneHandedEvents.OneHandedSettingsTogglesEvent.INVALID.getId();
        int metricsId = OneHandedUiEventLogger.OneHandedSettingsTogglesEvent.INVALID.getId();
        switch (newTimeout) {
            case OneHandedSettingsUtil.ONE_HANDED_TIMEOUT_NEVER:
                metricsId = OneHandedEvents.EVENT_ONE_HANDED_SETTINGS_TIMEOUT_SECONDS_NEVER;
                metricsId = OneHandedUiEventLogger.EVENT_ONE_HANDED_SETTINGS_TIMEOUT_SECONDS_NEVER;
                break;
            case OneHandedSettingsUtil.ONE_HANDED_TIMEOUT_SHORT_IN_SECONDS:
                metricsId = OneHandedEvents.EVENT_ONE_HANDED_SETTINGS_TIMEOUT_SECONDS_4;
                metricsId = OneHandedUiEventLogger.EVENT_ONE_HANDED_SETTINGS_TIMEOUT_SECONDS_4;
                break;
            case OneHandedSettingsUtil.ONE_HANDED_TIMEOUT_MEDIUM_IN_SECONDS:
                metricsId = OneHandedEvents.EVENT_ONE_HANDED_SETTINGS_TIMEOUT_SECONDS_8;
                metricsId = OneHandedUiEventLogger.EVENT_ONE_HANDED_SETTINGS_TIMEOUT_SECONDS_8;
                break;
            case OneHandedSettingsUtil.ONE_HANDED_TIMEOUT_LONG_IN_SECONDS:
                metricsId = OneHandedEvents.EVENT_ONE_HANDED_SETTINGS_TIMEOUT_SECONDS_12;
                metricsId = OneHandedUiEventLogger.EVENT_ONE_HANDED_SETTINGS_TIMEOUT_SECONDS_12;
                break;
            default:
                // do nothing
                break;
        }
        OneHandedEvents.writeEvent(metricsId);
        mOneHandedUiEventLogger.writeEvent(metricsId);

        if (mTimeoutHandler != null) {
            mTimeoutHandler.setTimeout(newTimeout);
@@ -377,9 +387,9 @@ public class OneHandedController {
    private void onTaskChangeExitSettingChanged() {
        final boolean enabled = OneHandedSettingsUtil.getSettingsTapsAppToExit(
                mContext.getContentResolver());
        OneHandedEvents.writeEvent(enabled
                ? OneHandedEvents.EVENT_ONE_HANDED_SETTINGS_APP_TAPS_EXIT_ON
                : OneHandedEvents.EVENT_ONE_HANDED_SETTINGS_APP_TAPS_EXIT_OFF);
        mOneHandedUiEventLogger.writeEvent(enabled
                ? OneHandedUiEventLogger.EVENT_ONE_HANDED_SETTINGS_APP_TAPS_EXIT_ON
                : OneHandedUiEventLogger.EVENT_ONE_HANDED_SETTINGS_APP_TAPS_EXIT_OFF);

        setTaskChangeToExit(enabled);
    }
@@ -397,9 +407,8 @@ public class OneHandedController {
    }

    private void setupTimeoutListener() {
        mTimeoutHandler.registerTimeoutListener(timeoutTime -> {
            stopOneHanded(OneHandedEvents.EVENT_ONE_HANDED_TRIGGER_TIMEOUT_OUT);
        });
        mTimeoutHandler.registerTimeoutListener(timeoutTime -> stopOneHanded(
                OneHandedUiEventLogger.EVENT_ONE_HANDED_TRIGGER_TIMEOUT_OUT));
    }

    /**
+30 −51
Original line number Diff line number Diff line
@@ -19,17 +19,13 @@ package com.android.wm.shell.onehanded;
import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.logging.UiEvent;
import com.android.internal.logging.UiEventLogger;
import com.android.internal.logging.UiEventLoggerImpl;

/**
 *  Interesting events related to the One-Handed.
 *  Helper class that ends OneHanded mode log to UiEvent, see also go/uievent
 */
public class OneHandedEvents {
    private static final String TAG = "OneHandedEvents";

    public static Callback sCallback;
    @VisibleForTesting
    static UiEventLogger sUiEventLogger = new UiEventLoggerImpl();
public class OneHandedUiEventLogger {
    private static final String TAG = "OneHandedUiEventLogger";
    private final UiEventLogger mUiEventLogger;

    /**
     * One-Handed event types
@@ -76,6 +72,10 @@ public class OneHandedEvents {
            "one_handed_settings_timeout_seconds_12"
    };

    public OneHandedUiEventLogger(UiEventLogger uiEventLogger) {
        mUiEventLogger = uiEventLogger;
    }

    /**
     * Events definition that related to One-Handed gestures.
     */
@@ -112,6 +112,7 @@ public class OneHandedEvents {
            mId = id;
        }

        @Override
        public int getId() {
            return mId;
        }
@@ -159,6 +160,7 @@ public class OneHandedEvents {
            mId = id;
        }

        @Override
        public int getId() {
            return mId;
        }
@@ -169,12 +171,8 @@ public class OneHandedEvents {
     * Logs an event to the system log, to sCallback if present, and to the logEvent destinations.
     * @param tag One of the EVENT_* codes above.
     */
    public static void writeEvent(int tag) {
        final long time = System.currentTimeMillis();
    public void writeEvent(int tag) {
        logEvent(tag);
        if (sCallback != null) {
            sCallback.writeEvent(time, tag);
        }
    }

    /**
@@ -183,94 +181,75 @@ public class OneHandedEvents {
     * @return String a readable description of the event.  Begins "writeEvent <tag_description>"
     * if the tag is valid.
     */
    public static String logEvent(int event) {
        if (event >= EVENT_TAGS.length) {
            return "";
        }
        final StringBuilder sb = new StringBuilder("writeEvent ").append(EVENT_TAGS[event]);
    private void logEvent(int event) {
        switch (event) {
            // Triggers
            case EVENT_ONE_HANDED_TRIGGER_GESTURE_IN:
                sUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_GESTURE_IN);
                mUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_GESTURE_IN);
                break;
            case EVENT_ONE_HANDED_TRIGGER_GESTURE_OUT:
                sUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_GESTURE_OUT);
                mUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_GESTURE_OUT);
                break;
            case EVENT_ONE_HANDED_TRIGGER_OVERSPACE_OUT:
                sUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_OVERSPACE_OUT);
                mUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_OVERSPACE_OUT);
                break;
            case EVENT_ONE_HANDED_TRIGGER_POP_IME_OUT:
                sUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_POP_IME_OUT);
                mUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_POP_IME_OUT);
                break;
            case EVENT_ONE_HANDED_TRIGGER_ROTATION_OUT:
                sUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_ROTATION_OUT);
                mUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_ROTATION_OUT);
                break;
            case EVENT_ONE_HANDED_TRIGGER_APP_TAPS_OUT:
                sUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_APP_TAPS_OUT);
                mUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_APP_TAPS_OUT);
                break;
            case EVENT_ONE_HANDED_TRIGGER_TIMEOUT_OUT:
                sUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_TIMEOUT_OUT);
                mUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_TIMEOUT_OUT);
                break;
            case EVENT_ONE_HANDED_TRIGGER_SCREEN_OFF_OUT:
                sUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_SCREEN_OFF_OUT);
                mUiEventLogger.log(OneHandedTriggerEvent.ONE_HANDED_TRIGGER_SCREEN_OFF_OUT);
                break;
            // Settings
            case EVENT_ONE_HANDED_SETTINGS_ENABLED_ON:
                sUiEventLogger.log(OneHandedSettingsTogglesEvent
                mUiEventLogger.log(OneHandedSettingsTogglesEvent
                        .ONE_HANDED_SETTINGS_TOGGLES_ENABLED_ON);
                break;
            case EVENT_ONE_HANDED_SETTINGS_ENABLED_OFF:
                sUiEventLogger.log(OneHandedSettingsTogglesEvent
                mUiEventLogger.log(OneHandedSettingsTogglesEvent
                        .ONE_HANDED_SETTINGS_TOGGLES_ENABLED_OFF);
                break;
            case EVENT_ONE_HANDED_SETTINGS_APP_TAPS_EXIT_ON:
                sUiEventLogger.log(OneHandedSettingsTogglesEvent
                mUiEventLogger.log(OneHandedSettingsTogglesEvent
                        .ONE_HANDED_SETTINGS_TOGGLES_APP_TAPS_EXIT_ON);
                break;
            case EVENT_ONE_HANDED_SETTINGS_APP_TAPS_EXIT_OFF:
                sUiEventLogger.log(OneHandedSettingsTogglesEvent
                mUiEventLogger.log(OneHandedSettingsTogglesEvent
                        .ONE_HANDED_SETTINGS_TOGGLES_APP_TAPS_EXIT_OFF);
                break;
            case EVENT_ONE_HANDED_SETTINGS_TIMEOUT_EXIT_ON:
                sUiEventLogger.log(OneHandedSettingsTogglesEvent
                mUiEventLogger.log(OneHandedSettingsTogglesEvent
                        .ONE_HANDED_SETTINGS_TOGGLES_TIMEOUT_EXIT_ON);
                break;
            case EVENT_ONE_HANDED_SETTINGS_TIMEOUT_EXIT_OFF:
                sUiEventLogger.log(OneHandedSettingsTogglesEvent
                mUiEventLogger.log(OneHandedSettingsTogglesEvent
                        .ONE_HANDED_SETTINGS_TOGGLES_TIMEOUT_EXIT_OFF);
                break;
            case EVENT_ONE_HANDED_SETTINGS_TIMEOUT_SECONDS_NEVER:
                sUiEventLogger.log(OneHandedSettingsTogglesEvent
                mUiEventLogger.log(OneHandedSettingsTogglesEvent
                        .ONE_HANDED_SETTINGS_TOGGLES_TIMEOUT_SECONDS_NEVER);
                break;
            case EVENT_ONE_HANDED_SETTINGS_TIMEOUT_SECONDS_4:
                sUiEventLogger.log(OneHandedSettingsTogglesEvent
                mUiEventLogger.log(OneHandedSettingsTogglesEvent
                        .ONE_HANDED_SETTINGS_TOGGLES_TIMEOUT_SECONDS_4);
                break;
            case EVENT_ONE_HANDED_SETTINGS_TIMEOUT_SECONDS_8:
                sUiEventLogger.log(OneHandedSettingsTogglesEvent
                mUiEventLogger.log(OneHandedSettingsTogglesEvent
                        .ONE_HANDED_SETTINGS_TOGGLES_TIMEOUT_SECONDS_8);
                break;
            case EVENT_ONE_HANDED_SETTINGS_TIMEOUT_SECONDS_12:
                sUiEventLogger.log(OneHandedSettingsTogglesEvent
                mUiEventLogger.log(OneHandedSettingsTogglesEvent
                        .ONE_HANDED_SETTINGS_TOGGLES_TIMEOUT_SECONDS_12);
                break;
            default:
                // Do nothing
                break;
        }
        return sb.toString();
    }

    /**
     * An interface for logging an event to the system log, if Callback present.
     */
    public interface Callback {
        /**
         *
         * @param time System current time.
         * @param tag Event tag.
         */
        void writeEvent(long time, int tag);
    }
}
+3 −1
Original line number Diff line number Diff line
@@ -28,7 +28,6 @@ import android.content.om.IOverlayManager;
import android.os.Handler;
import android.provider.Settings;
import android.testing.AndroidTestingRunner;
import android.testing.TestableLooper;
import android.view.Display;

import androidx.test.filters.SmallTest;
@@ -67,6 +66,8 @@ public class OneHandedControllerTest extends OneHandedTestCase {
    @Mock
    OneHandedTimeoutHandler mMockTimeoutHandler;
    @Mock
    OneHandedUiEventLogger mMockUiEventLogger;
    @Mock
    IOverlayManager mMockOverlayManager;
    @Mock
    TaskStackListenerImpl mMockTaskStackListener;
@@ -89,6 +90,7 @@ public class OneHandedControllerTest extends OneHandedTestCase {
                mMockTutorialHandler,
                mMockGestureHandler,
                mTimeoutHandler,
                mMockUiEventLogger,
                mMockOverlayManager,
                mMockTaskStackListener,
                mMockShellMainExecutor,
+4 −1
Original line number Diff line number Diff line
@@ -21,7 +21,6 @@ import static org.mockito.Mockito.verify;
import android.content.om.IOverlayManager;
import android.os.Handler;
import android.testing.AndroidTestingRunner;
import android.testing.TestableLooper;

import androidx.test.filters.SmallTest;

@@ -58,6 +57,9 @@ public class OneHandedTutorialHandlerTest extends OneHandedTestCase {
    ShellExecutor mMockShellMainExecutor;
    @Mock
    Handler mMockShellMainHandler;
    @Mock
    OneHandedUiEventLogger mMockUiEventLogger;


    @Before
    public void setUp() {
@@ -75,6 +77,7 @@ public class OneHandedTutorialHandlerTest extends OneHandedTestCase {
                mTutorialHandler,
                mGestureHandler,
                mTimeoutHandler,
                mMockUiEventLogger,
                mMockOverlayManager,
                mMockTaskStackListener,
                mMockShellMainExecutor,
Loading