mirror of
https://github.com/LawnchairLauncher/lawnchair.git
synced 2026-02-19 02:38:20 +00:00
Merge "Fix NPE of handling ACTION_MOVE in StatusBarTouchController and added unit test" into udc-dev am: 3dca7b3c6a
Original change: https://googleplex-android-review.googlesource.com/c/platform/packages/apps/Launcher3/+/23300979 Change-Id: I640176031e4843bfdfa1358a253afebe90a384b7 Signed-off-by: Automerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>
This commit is contained in:
@@ -30,6 +30,8 @@ import android.view.ViewConfiguration;
|
||||
import android.view.Window;
|
||||
import android.view.WindowManager;
|
||||
|
||||
import androidx.annotation.VisibleForTesting;
|
||||
|
||||
import com.android.launcher3.AbstractFloatingView;
|
||||
import com.android.launcher3.DeviceProfile;
|
||||
import com.android.launcher3.Launcher;
|
||||
@@ -50,12 +52,13 @@ public class StatusBarTouchController implements TouchController {
|
||||
|
||||
private final Launcher mLauncher;
|
||||
private final SystemUiProxy mSystemUiProxy;
|
||||
private final float mTouchSlop;
|
||||
@VisibleForTesting final float mTouchSlop;
|
||||
private int mLastAction;
|
||||
private final SparseArray<PointF> mDownEvents;
|
||||
|
||||
/* If {@code false}, this controller should not handle the input {@link MotionEvent}.*/
|
||||
private boolean mCanIntercept;
|
||||
@VisibleForTesting
|
||||
boolean mCanIntercept;
|
||||
|
||||
public StatusBarTouchController(Launcher l) {
|
||||
mLauncher = l;
|
||||
@@ -82,9 +85,9 @@ public class StatusBarTouchController implements TouchController {
|
||||
|
||||
@Override
|
||||
public final boolean onControllerInterceptTouchEvent(MotionEvent ev) {
|
||||
int action = ev.getActionMasked();
|
||||
int idx = ev.getActionIndex();
|
||||
int pid = ev.getPointerId(idx);
|
||||
final int action = ev.getActionMasked();
|
||||
final int idx = ev.getActionIndex();
|
||||
final int pid = ev.getPointerId(idx);
|
||||
if (action == ACTION_DOWN) {
|
||||
mCanIntercept = canInterceptTouch(ev);
|
||||
if (!mCanIntercept) {
|
||||
@@ -92,14 +95,14 @@ public class StatusBarTouchController implements TouchController {
|
||||
}
|
||||
mDownEvents.clear();
|
||||
mDownEvents.put(pid, new PointF(ev.getX(), ev.getY()));
|
||||
} else if (ev.getActionMasked() == MotionEvent.ACTION_POINTER_DOWN) {
|
||||
} else if (action == MotionEvent.ACTION_POINTER_DOWN) {
|
||||
// Check!! should only set it only when threshold is not entered.
|
||||
mDownEvents.put(pid, new PointF(ev.getX(idx), ev.getY(idx)));
|
||||
}
|
||||
if (!mCanIntercept) {
|
||||
return false;
|
||||
}
|
||||
if (action == ACTION_MOVE) {
|
||||
if (action == ACTION_MOVE && mDownEvents.contains(pid)) {
|
||||
float dy = ev.getY(idx) - mDownEvents.get(pid).y;
|
||||
float dx = ev.getX(idx) - mDownEvents.get(pid).x;
|
||||
// Currently input dispatcher will not do touch transfer if there are more than
|
||||
@@ -126,7 +129,6 @@ public class StatusBarTouchController implements TouchController {
|
||||
mLauncher.getStatsLogManager().logger()
|
||||
.log(LAUNCHER_SWIPE_DOWN_WORKSPACE_NOTISHADE_OPEN);
|
||||
setWindowSlippery(false);
|
||||
return true;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
@@ -140,7 +142,8 @@ public class StatusBarTouchController implements TouchController {
|
||||
* Touches can slide out of the window but they cannot necessarily slide
|
||||
* back in (unless the other window with touch focus permits it).
|
||||
*/
|
||||
private void setWindowSlippery(boolean enable) {
|
||||
@VisibleForTesting
|
||||
void setWindowSlippery(boolean enable) {
|
||||
Window w = mLauncher.getWindow();
|
||||
WindowManager.LayoutParams wlp = w.getAttributes();
|
||||
if (enable) {
|
||||
|
||||
@@ -0,0 +1,152 @@
|
||||
/*
|
||||
* Copyright (C) 202 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.uioverrides.touchcontrollers
|
||||
|
||||
import android.view.MotionEvent
|
||||
import android.view.WindowManager
|
||||
import androidx.test.filters.SmallTest
|
||||
import androidx.test.runner.AndroidJUnit4
|
||||
import com.android.launcher3.Launcher
|
||||
import com.android.launcher3.ui.AbstractLauncherUiTest
|
||||
import com.android.launcher3.ui.TaplTestsLauncher3
|
||||
import junit.framework.Assert.assertEquals
|
||||
import junit.framework.Assert.assertFalse
|
||||
import junit.framework.Assert.assertTrue
|
||||
import org.junit.Before
|
||||
import org.junit.Test
|
||||
import org.junit.runner.RunWith
|
||||
|
||||
@SmallTest
|
||||
@RunWith(AndroidJUnit4::class)
|
||||
class StatusBarTouchControllerTest : AbstractLauncherUiTest() {
|
||||
@Before
|
||||
@Throws(Exception::class)
|
||||
fun setup() {
|
||||
TaplTestsLauncher3.initialize(this)
|
||||
}
|
||||
|
||||
@Test
|
||||
fun interceptActionDown_canIntercept() {
|
||||
executeOnLauncher { launcher: Launcher? ->
|
||||
val underTest = StatusBarTouchController(launcher)
|
||||
assertFalse(underTest.mCanIntercept)
|
||||
val downEvent = MotionEvent.obtain(1, 1, MotionEvent.ACTION_DOWN, 0f, 0f, 0)
|
||||
|
||||
underTest.onControllerInterceptTouchEvent(downEvent)
|
||||
|
||||
assertTrue(underTest.mCanIntercept)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun interceptActionMove_handledAndSetSlippery() {
|
||||
executeOnLauncher { launcher: Launcher ->
|
||||
val underTest = StatusBarTouchController(launcher)
|
||||
val downEvent = MotionEvent.obtain(1, 1, MotionEvent.ACTION_DOWN, 0f, 0f, 0)
|
||||
underTest.onControllerInterceptTouchEvent(downEvent)
|
||||
val w = launcher.window
|
||||
assertEquals(0, w.attributes.flags and WindowManager.LayoutParams.FLAG_SLIPPERY)
|
||||
val moveEvent =
|
||||
MotionEvent.obtain(
|
||||
2,
|
||||
2,
|
||||
MotionEvent.ACTION_MOVE,
|
||||
underTest.mTouchSlop,
|
||||
underTest.mTouchSlop + 10,
|
||||
0
|
||||
)
|
||||
|
||||
val handled = underTest.onControllerInterceptTouchEvent(moveEvent)
|
||||
|
||||
assertTrue(handled)
|
||||
assertEquals(
|
||||
WindowManager.LayoutParams.FLAG_SLIPPERY,
|
||||
w.attributes.flags and WindowManager.LayoutParams.FLAG_SLIPPERY
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun interceptActionMove_not_handled() {
|
||||
executeOnLauncher { launcher: Launcher? ->
|
||||
val underTest = StatusBarTouchController(launcher)
|
||||
val downEvent = MotionEvent.obtain(1, 1, MotionEvent.ACTION_DOWN, 0f, 0f, 0)
|
||||
underTest.onControllerInterceptTouchEvent(downEvent)
|
||||
val moveEvent =
|
||||
MotionEvent.obtain(
|
||||
2,
|
||||
2,
|
||||
MotionEvent.ACTION_MOVE,
|
||||
underTest.mTouchSlop + 10,
|
||||
underTest.mTouchSlop,
|
||||
0
|
||||
)
|
||||
|
||||
val handled = underTest.onControllerInterceptTouchEvent(moveEvent)
|
||||
|
||||
assertFalse(handled)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun interceptActionMoveAsFirstGestureEvent_notCrashedNorHandled() {
|
||||
executeOnLauncher { launcher: Launcher? ->
|
||||
val underTest = StatusBarTouchController(launcher)
|
||||
underTest.mCanIntercept = true
|
||||
val moveEvent = MotionEvent.obtain(2, 2, MotionEvent.ACTION_MOVE, 10f, 10f, 0)
|
||||
|
||||
val handled = underTest.onControllerInterceptTouchEvent(moveEvent)
|
||||
|
||||
assertFalse(handled)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun handleActionUp_setNotSlippery() {
|
||||
executeOnLauncher { launcher: Launcher ->
|
||||
val underTest = StatusBarTouchController(launcher)
|
||||
underTest.mCanIntercept = true
|
||||
underTest.setWindowSlippery(true)
|
||||
val moveEvent = MotionEvent.obtain(2, 2, MotionEvent.ACTION_UP, 10f, 10f, 0)
|
||||
|
||||
val handled = underTest.onControllerTouchEvent(moveEvent)
|
||||
|
||||
assertTrue(handled)
|
||||
assertEquals(
|
||||
0,
|
||||
launcher.window.attributes.flags and WindowManager.LayoutParams.FLAG_SLIPPERY
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun handleActionCancel_setNotSlippery() {
|
||||
executeOnLauncher { launcher: Launcher ->
|
||||
val underTest = StatusBarTouchController(launcher)
|
||||
underTest.mCanIntercept = true
|
||||
underTest.setWindowSlippery(true)
|
||||
val moveEvent = MotionEvent.obtain(2, 2, MotionEvent.ACTION_CANCEL, 10f, 10f, 0)
|
||||
|
||||
val handled = underTest.onControllerTouchEvent(moveEvent)
|
||||
|
||||
assertTrue(handled)
|
||||
assertEquals(
|
||||
0,
|
||||
launcher.window.attributes.flags and WindowManager.LayoutParams.FLAG_SLIPPERY
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user