0

ui: Add multi-step EventGenerator::MoveMouseBy/MoveTouch*

Add multi-step EventGenerator::MoveMouseBy/MoveTouch* that
generates multiple events to get to target location.
Multi-step `MoveMouseBy` will be used by a test in a follow-up CL.

Update callers to bind lamda instead of directly binding
`MoveMouseBy` since it is ambiguous now.

Bug: None
Change-Id: I808d572541dd5777cc2db1631969098b62613829
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6442199
Reviewed-by: Mitsuru Oshima <oshima@chromium.org>
Commit-Queue: Xiyuan Xia <xiyuan@chromium.org>
Cr-Commit-Position: refs/heads/main@{#1444863}
This commit is contained in:
Xiyuan Xia
2025-04-09 11:45:38 -07:00
committed by Chromium LUCI CQ
parent 8a957f7a45
commit 363ff8348a
4 changed files with 68 additions and 38 deletions

@ -1312,16 +1312,16 @@ TEST_F(DragDropControllerTest, EventTarget) {
generator.PressLeftButton();
// For drag enter
base::SingleThreadTaskRunner::GetCurrentDefault()->PostTask(
FROM_HERE, base::BindOnce(&ui::test::EventGenerator::MoveMouseBy,
base::Unretained(&generator), 0, 1));
FROM_HERE,
base::BindLambdaForTesting([&]() { generator.MoveMouseBy(0, 1); }));
// For drag update
base::SingleThreadTaskRunner::GetCurrentDefault()->PostTask(
FROM_HERE, base::BindOnce(&ui::test::EventGenerator::MoveMouseBy,
base::Unretained(&generator), 0, 1));
FROM_HERE,
base::BindLambdaForTesting([&]() { generator.MoveMouseBy(0, 1); }));
// For perform drop
base::SingleThreadTaskRunner::GetCurrentDefault()->PostTask(
FROM_HERE, base::BindOnce(&ui::test::EventGenerator::ReleaseLeftButton,
base::Unretained(&generator)));
FROM_HERE,
base::BindLambdaForTesting([&]() { generator.ReleaseLeftButton(); }));
drag_drop_controller_->set_should_block_during_drag_drop(true);
auto data = CreateDragData(/*with_image=*/false);
@ -1352,12 +1352,12 @@ TEST_F(DragDropControllerTest, DragTabChangesDragOperationToMove) {
generator.PressLeftButton();
// For drag enter.
base::SingleThreadTaskRunner::GetCurrentDefault()->PostTask(
FROM_HERE, base::BindOnce(&ui::test::EventGenerator::MoveMouseBy,
base::Unretained(&generator), 0, 1));
FROM_HERE,
base::BindLambdaForTesting([&]() { generator.MoveMouseBy(0, 1); }));
// For perform drop.
base::SingleThreadTaskRunner::GetCurrentDefault()->PostTask(
FROM_HERE, base::BindOnce(&ui::test::EventGenerator::ReleaseLeftButton,
base::Unretained(&generator)));
FROM_HERE,
base::BindLambdaForTesting([&]() { generator.ReleaseLeftButton(); }));
drag_drop_controller_->set_should_block_during_drag_drop(true);
DragOperation operation = drag_drop_controller_->StartDragAndDrop(

@ -81,6 +81,7 @@
#include "base/i18n/rtl.h"
#include "base/memory/raw_ptr.h"
#include "base/run_loop.h"
#include "base/test/bind.h"
#include "base/test/icu_test_util.h"
#include "base/test/metrics/histogram_tester.h"
#include "base/test/metrics/user_action_tester.h"
@ -2966,14 +2967,10 @@ class ShelfLayoutManagerDragDropTest
// Drags a view vertically by `dy` pixels. Assumes the drag has been started.
void MoveDragBy(int dy) {
auto move_fn =
base::BindRepeating(GetParam() == DragEventType::kMouse
? &ui::test::EventGenerator::MoveMouseBy
: &ui::test::EventGenerator::MoveTouchBy,
base::Unretained(generator_));
const int step = dy / abs(dy);
for (int i = 0; i < abs(dy); ++i) {
move_fn.Run(0, step);
if (GetParam() == DragEventType::kMouse) {
generator_->MoveMouseBy(0, dy, /*count=*/abs(dy));
} else {
generator_->MoveTouchBy(0, dy, /*count=*/abs(dy));
}
}

@ -341,19 +341,42 @@ void EventGenerator::PressTouchId(
Dispatch(&touchev);
}
void EventGenerator::MoveTouch(const gfx::Point& point) {
MoveTouchId(point, 0);
void EventGenerator::MoveTouch(const gfx::Point& point, int count) {
MoveTouchId(point, 0, count);
}
void EventGenerator::MoveTouchId(const gfx::Point& point, int touch_id) {
SetCurrentScreenLocation(point);
ui::TouchEvent touchev = CreateTestTouchEvent(
ui::EventType::kTouchMoved, GetLocationInCurrentRoot(), touch_id, flags_,
ui::EventTimeForNow());
Dispatch(&touchev);
void EventGenerator::MoveTouchId(const gfx::Point& point,
int touch_id,
int count) {
// Tracks the location of last `SetCurrentScreenLocation` in the loop.
gfx::Point expected_current_location = current_screen_location_;
if (!grab_)
UpdateCurrentDispatcher(point);
const gfx::Point start_point = current_screen_location_;
const gfx::Vector2dF diff(point - start_point);
for (float i = 1; i <= count; i++) {
gfx::Vector2dF step(diff);
step.Scale(i / count);
gfx::Point move_point = start_point + gfx::ToRoundedVector2d(step);
if (!grab_) {
UpdateCurrentDispatcher(move_point);
}
// Changing `current_screen_location_` in nested `MoveTouchId` under
// `Dispatch` is not supported.
CHECK_EQ(expected_current_location, current_screen_location_);
// Update current location before dispatching because some tests (e.g.
// apps grid view dragging related) calculate the next touch position
// during the dispatch.
SetCurrentScreenLocation(move_point);
expected_current_location = move_point;
delegate()->ConvertPointToTarget(current_target_, &move_point);
ui::TouchEvent touchev =
CreateTestTouchEvent(ui::EventType::kTouchMoved, move_point, touch_id,
flags_, ui::EventTimeForNow());
Dispatch(&touchev);
}
}
void EventGenerator::ReleaseTouch() {

@ -257,8 +257,9 @@ class EventGenerator {
MoveMouseRelativeTo(window, gfx::Point(x, y));
}
void MoveMouseBy(int x, int y) {
MoveMouseTo(current_screen_location_ + gfx::Vector2d(x, y));
void MoveMouseBy(int x, int y) { MoveMouseBy(x, y, /*count=*/1); }
void MoveMouseBy(int x, int y, int count) {
MoveMouseTo(current_screen_location_ + gfx::Vector2d(x, y), count);
}
// Generates events to drag mouse to given |point|.
@ -312,22 +313,31 @@ class EventGenerator {
int touch_id,
const std::optional<gfx::Point>& touch_location_in_screen = std::nullopt);
// Generates a EventType::kTouchMoved event to |point|.
void MoveTouch(const gfx::Point& point);
// Generates EventType::kTouchMoved events to |point|.
void MoveTouch(const gfx::Point& point, int count);
void MoveTouch(const gfx::Point& point) { MoveTouch(point, /*count=*/1); }
// Generates a EventType::kTouchMoved event moving by (x, y) from current
// Generates EventType::kTouchMoved events moving by (x, y) from current
// location.
void MoveTouchBy(int x, int y) {
MoveTouch(current_screen_location_ + gfx::Vector2d(x, y));
void MoveTouchBy(int x, int y, int count) {
MoveTouch(current_screen_location_ + gfx::Vector2d(x, y), count);
}
void MoveTouchBy(int x, int y) { MoveTouchBy(x, y, /*count=*/1); }
// Generates a EventType::kTouchMoved event to |point| with |touch_id|.
void MoveTouchId(const gfx::Point& point, int touch_id);
// Generates EventType::kTouchMoved events to |point| with |touch_id|.
void MoveTouchId(const gfx::Point& point, int touch_id, int count);
void MoveTouchId(const gfx::Point& point, int touch_id) {
MoveTouchId(point, touch_id, /*count=*/1);
}
// Generates a EventType::kTouchMoved event moving (x, y) from current
// location with |touch_id|.
void MoveTouchIdBy(int touch_id, int x, int y, int count) {
MoveTouchId(current_screen_location_ + gfx::Vector2d(x, y), touch_id,
count);
}
void MoveTouchIdBy(int touch_id, int x, int y) {
MoveTouchId(current_screen_location_ + gfx::Vector2d(x, y), touch_id);
MoveTouchIdBy(touch_id, x, y, /*count=*/1);
}
// Generates a touch release event.