Loading src/com/android/launcher3/CheckLongPressHelper.java +3 −12 Original line number Diff line number Diff line Loading @@ -17,11 +17,12 @@ package com.android.launcher3; import android.os.Handler; import android.view.InputDevice; import android.view.MotionEvent; import android.view.View; import android.view.ViewConfiguration; import com.android.launcher3.util.TouchUtil; /** * Utility class to handle tripper long press or right click on a view with custom timeout and * stylus event Loading Loading @@ -64,7 +65,7 @@ public class CheckLongPressHelper { cancelLongPress(); // Mouse right click should immediately trigger a long press if (isMouseRightClickDownOrMove(ev)) { if (TouchUtil.isMouseRightClickDownOrMove(ev)) { mIsInMouseRightClick = true; triggerLongPress(); final Handler handler = mView.getHandler(); Loading Loading @@ -176,14 +177,4 @@ public class CheckLongPressHelper { return event.getToolType(0) == MotionEvent.TOOL_TYPE_STYLUS && event.isButtonPressed(MotionEvent.BUTTON_SECONDARY); } /** * Detect ACTION_DOWN or ACTION_MOVE from mouse right button. Note that we cannot detect * ACTION_UP from mouse's right button because, in that case, * {@link MotionEvent#getButtonState()} returns 0 for any mouse button (right, middle, right). */ private static boolean isMouseRightClickDownOrMove(MotionEvent event) { return event.isFromSource(InputDevice.SOURCE_MOUSE) && ((event.getButtonState() & MotionEvent.BUTTON_SECONDARY) != 0); } } src/com/android/launcher3/touch/WorkspaceTouchListener.java +10 −0 Original line number Diff line number Diff line Loading @@ -44,6 +44,7 @@ import com.android.launcher3.dragndrop.DragLayer; import com.android.launcher3.logger.LauncherAtom; import com.android.launcher3.testing.TestLogging; import com.android.launcher3.testing.shared.TestProtocol; import com.android.launcher3.util.TouchUtil; /** * Helper class to handle touch on empty space in workspace and show options popup on long press Loading Loading @@ -105,6 +106,11 @@ public class WorkspaceTouchListener extends GestureDetector.SimpleOnGestureListe if (handleLongPress) { mLongPressState = STATE_REQUESTED; mTouchDownPoint.set(ev.getX(), ev.getY()); // Mouse right button's ACTION_DOWN should immediately show menu if (TouchUtil.isMouseRightClickDownOrMove(ev)) { maybeShowMenu(); return true; } } mWorkspace.onTouchEvent(ev); Loading Loading @@ -185,6 +191,10 @@ public class WorkspaceTouchListener extends GestureDetector.SimpleOnGestureListe @Override public void onLongPress(MotionEvent event) { maybeShowMenu(); } private void maybeShowMenu() { if (mLongPressState == STATE_REQUESTED) { TestLogging.recordEvent(TestProtocol.SEQUENCE_MAIN, "Workspace.longPress"); if (canHandleLongPress()) { Loading src/com/android/launcher3/util/TouchUtil.java 0 → 100644 +37 −0 Original line number Diff line number Diff line /* * Copyright (C) 2022 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.launcher3.util; import android.view.InputDevice; import android.view.MotionEvent; import androidx.annotation.NonNull; /** Util class for touch event. */ public final class TouchUtil { private TouchUtil() {} /** * Detect ACTION_DOWN or ACTION_MOVE from mouse right button. Note that we cannot detect * ACTION_UP from mouse's right button because, in that case, * {@link MotionEvent#getButtonState()} returns 0 for any mouse button (right, middle, right). */ public static boolean isMouseRightClickDownOrMove(@NonNull MotionEvent event) { return event.isFromSource(InputDevice.SOURCE_MOUSE) && ((event.getButtonState() & MotionEvent.BUTTON_SECONDARY) != 0); } } tests/src/com/android/launcher3/util/TouchUtilTest.kt 0 → 100644 +67 −0 Original line number Diff line number Diff line /* * Copyright (C) 2022 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.launcher3.util import android.view.InputDevice import android.view.MotionEvent import androidx.test.filters.SmallTest import com.google.common.truth.Truth.assertThat import androidx.test.ext.junit.runners.AndroidJUnit4 import org.junit.Test import org.junit.runner.RunWith /** Unit tests for [TouchUtil] */ @SmallTest @RunWith(AndroidJUnit4::class) class TouchUtilTest { @Test fun isMouseRightClickDownOrMove_onMouseRightButton_returnsTrue() { val ev = MotionEvent.obtain(200, 300, MotionEvent.ACTION_MOVE, 1.0f, 0.0f, 0) ev.source = InputDevice.SOURCE_MOUSE ev.buttonState = MotionEvent.BUTTON_SECONDARY assertThat(TouchUtil.isMouseRightClickDownOrMove(ev)).isTrue() } @Test fun isMouseRightClickDownOrMove_onMouseLeftButton_returnsFalse() { val ev = MotionEvent.obtain(200, 300, MotionEvent.ACTION_MOVE, 1.0f, 0.0f, 0) ev.source = InputDevice.SOURCE_MOUSE ev.buttonState = MotionEvent.BUTTON_PRIMARY assertThat(TouchUtil.isMouseRightClickDownOrMove(ev)).isFalse() } @Test fun isMouseRightClickDownOrMove_onMouseTertiaryButton_returnsFalse() { val ev = MotionEvent.obtain(200, 300, MotionEvent.ACTION_MOVE, 1.0f, 0.0f, 0) ev.source = InputDevice.SOURCE_MOUSE ev.buttonState = MotionEvent.BUTTON_TERTIARY assertThat(TouchUtil.isMouseRightClickDownOrMove(ev)).isFalse() } @Test fun isMouseRightClickDownOrMove_onDpadRightButton_returnsFalse() { val ev = MotionEvent.obtain(200, 300, MotionEvent.ACTION_MOVE, 1.0f, 0.0f, 0) ev.source = InputDevice.SOURCE_DPAD ev.buttonState = MotionEvent.BUTTON_SECONDARY assertThat(TouchUtil.isMouseRightClickDownOrMove(ev)).isFalse() } } Loading
src/com/android/launcher3/CheckLongPressHelper.java +3 −12 Original line number Diff line number Diff line Loading @@ -17,11 +17,12 @@ package com.android.launcher3; import android.os.Handler; import android.view.InputDevice; import android.view.MotionEvent; import android.view.View; import android.view.ViewConfiguration; import com.android.launcher3.util.TouchUtil; /** * Utility class to handle tripper long press or right click on a view with custom timeout and * stylus event Loading Loading @@ -64,7 +65,7 @@ public class CheckLongPressHelper { cancelLongPress(); // Mouse right click should immediately trigger a long press if (isMouseRightClickDownOrMove(ev)) { if (TouchUtil.isMouseRightClickDownOrMove(ev)) { mIsInMouseRightClick = true; triggerLongPress(); final Handler handler = mView.getHandler(); Loading Loading @@ -176,14 +177,4 @@ public class CheckLongPressHelper { return event.getToolType(0) == MotionEvent.TOOL_TYPE_STYLUS && event.isButtonPressed(MotionEvent.BUTTON_SECONDARY); } /** * Detect ACTION_DOWN or ACTION_MOVE from mouse right button. Note that we cannot detect * ACTION_UP from mouse's right button because, in that case, * {@link MotionEvent#getButtonState()} returns 0 for any mouse button (right, middle, right). */ private static boolean isMouseRightClickDownOrMove(MotionEvent event) { return event.isFromSource(InputDevice.SOURCE_MOUSE) && ((event.getButtonState() & MotionEvent.BUTTON_SECONDARY) != 0); } }
src/com/android/launcher3/touch/WorkspaceTouchListener.java +10 −0 Original line number Diff line number Diff line Loading @@ -44,6 +44,7 @@ import com.android.launcher3.dragndrop.DragLayer; import com.android.launcher3.logger.LauncherAtom; import com.android.launcher3.testing.TestLogging; import com.android.launcher3.testing.shared.TestProtocol; import com.android.launcher3.util.TouchUtil; /** * Helper class to handle touch on empty space in workspace and show options popup on long press Loading Loading @@ -105,6 +106,11 @@ public class WorkspaceTouchListener extends GestureDetector.SimpleOnGestureListe if (handleLongPress) { mLongPressState = STATE_REQUESTED; mTouchDownPoint.set(ev.getX(), ev.getY()); // Mouse right button's ACTION_DOWN should immediately show menu if (TouchUtil.isMouseRightClickDownOrMove(ev)) { maybeShowMenu(); return true; } } mWorkspace.onTouchEvent(ev); Loading Loading @@ -185,6 +191,10 @@ public class WorkspaceTouchListener extends GestureDetector.SimpleOnGestureListe @Override public void onLongPress(MotionEvent event) { maybeShowMenu(); } private void maybeShowMenu() { if (mLongPressState == STATE_REQUESTED) { TestLogging.recordEvent(TestProtocol.SEQUENCE_MAIN, "Workspace.longPress"); if (canHandleLongPress()) { Loading
src/com/android/launcher3/util/TouchUtil.java 0 → 100644 +37 −0 Original line number Diff line number Diff line /* * Copyright (C) 2022 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.launcher3.util; import android.view.InputDevice; import android.view.MotionEvent; import androidx.annotation.NonNull; /** Util class for touch event. */ public final class TouchUtil { private TouchUtil() {} /** * Detect ACTION_DOWN or ACTION_MOVE from mouse right button. Note that we cannot detect * ACTION_UP from mouse's right button because, in that case, * {@link MotionEvent#getButtonState()} returns 0 for any mouse button (right, middle, right). */ public static boolean isMouseRightClickDownOrMove(@NonNull MotionEvent event) { return event.isFromSource(InputDevice.SOURCE_MOUSE) && ((event.getButtonState() & MotionEvent.BUTTON_SECONDARY) != 0); } }
tests/src/com/android/launcher3/util/TouchUtilTest.kt 0 → 100644 +67 −0 Original line number Diff line number Diff line /* * Copyright (C) 2022 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.launcher3.util import android.view.InputDevice import android.view.MotionEvent import androidx.test.filters.SmallTest import com.google.common.truth.Truth.assertThat import androidx.test.ext.junit.runners.AndroidJUnit4 import org.junit.Test import org.junit.runner.RunWith /** Unit tests for [TouchUtil] */ @SmallTest @RunWith(AndroidJUnit4::class) class TouchUtilTest { @Test fun isMouseRightClickDownOrMove_onMouseRightButton_returnsTrue() { val ev = MotionEvent.obtain(200, 300, MotionEvent.ACTION_MOVE, 1.0f, 0.0f, 0) ev.source = InputDevice.SOURCE_MOUSE ev.buttonState = MotionEvent.BUTTON_SECONDARY assertThat(TouchUtil.isMouseRightClickDownOrMove(ev)).isTrue() } @Test fun isMouseRightClickDownOrMove_onMouseLeftButton_returnsFalse() { val ev = MotionEvent.obtain(200, 300, MotionEvent.ACTION_MOVE, 1.0f, 0.0f, 0) ev.source = InputDevice.SOURCE_MOUSE ev.buttonState = MotionEvent.BUTTON_PRIMARY assertThat(TouchUtil.isMouseRightClickDownOrMove(ev)).isFalse() } @Test fun isMouseRightClickDownOrMove_onMouseTertiaryButton_returnsFalse() { val ev = MotionEvent.obtain(200, 300, MotionEvent.ACTION_MOVE, 1.0f, 0.0f, 0) ev.source = InputDevice.SOURCE_MOUSE ev.buttonState = MotionEvent.BUTTON_TERTIARY assertThat(TouchUtil.isMouseRightClickDownOrMove(ev)).isFalse() } @Test fun isMouseRightClickDownOrMove_onDpadRightButton_returnsFalse() { val ev = MotionEvent.obtain(200, 300, MotionEvent.ACTION_MOVE, 1.0f, 0.0f, 0) ev.source = InputDevice.SOURCE_DPAD ev.buttonState = MotionEvent.BUTTON_SECONDARY assertThat(TouchUtil.isMouseRightClickDownOrMove(ev)).isFalse() } }