Coverage Report

Created: 2018-09-25 14:53

/src/mozilla-central/layout/base/gtest/TestAccessibleCaretEventHub.cpp
Line
Count
Source (jump to first uncovered line)
1
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
3
/* This Source Code Form is subject to the terms of the Mozilla Public
4
 * License, v. 2.0. If a copy of the MPL was not distributed with this
5
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
7
#include "gtest/gtest.h"
8
#include "gmock/gmock.h"
9
10
#include <iostream>
11
#include <string>
12
13
#include "AccessibleCaretManager.h"
14
#include "gfxPrefs.h"
15
#include "mozilla/AccessibleCaretEventHub.h"
16
#include "mozilla/BasicEvents.h"
17
#include "mozilla/MouseEvents.h"
18
#include "mozilla/TouchEvents.h"
19
20
using ::testing::AtLeast;
21
using ::testing::DefaultValue;
22
using ::testing::Eq;
23
using ::testing::InSequence;
24
using ::testing::MockFunction;
25
using ::testing::Return;
26
using ::testing::_;
27
28
// -----------------------------------------------------------------------------
29
// This file test the state transitions of AccessibleCaretEventHub under
30
// various combination of events and callbacks.
31
32
namespace mozilla
33
{
34
35
class MockAccessibleCaretManager : public AccessibleCaretManager
36
{
37
public:
38
  MockAccessibleCaretManager()
39
    : AccessibleCaretManager(nullptr)
40
0
  {
41
0
  }
42
43
  MOCK_METHOD2(PressCaret,
44
               nsresult(const nsPoint& aPoint, EventClassID aEventClass));
45
  MOCK_METHOD1(DragCaret, nsresult(const nsPoint& aPoint));
46
  MOCK_METHOD0(ReleaseCaret, nsresult());
47
  MOCK_METHOD1(TapCaret, nsresult(const nsPoint& aPoint));
48
  MOCK_METHOD1(SelectWordOrShortcut, nsresult(const nsPoint& aPoint));
49
  MOCK_METHOD0(OnScrollStart, void());
50
  MOCK_METHOD0(OnScrollEnd, void());
51
  MOCK_METHOD0(OnScrollPositionChanged, void());
52
  MOCK_METHOD0(OnBlur, void());
53
};
54
55
class MockAccessibleCaretEventHub : public AccessibleCaretEventHub
56
{
57
public:
58
  using AccessibleCaretEventHub::NoActionState;
59
  using AccessibleCaretEventHub::PressCaretState;
60
  using AccessibleCaretEventHub::DragCaretState;
61
  using AccessibleCaretEventHub::PressNoCaretState;
62
  using AccessibleCaretEventHub::ScrollState;
63
  using AccessibleCaretEventHub::LongTapState;
64
65
  MockAccessibleCaretEventHub()
66
    : AccessibleCaretEventHub(nullptr)
67
0
  {
68
0
    mManager = MakeUnique<MockAccessibleCaretManager>();
69
0
    mInitialized = true;
70
0
  }
71
72
  nsPoint GetTouchEventPosition(WidgetTouchEvent* aEvent,
73
                                int32_t aIdentifier) const override
74
0
  {
75
0
    // Return the device point directly.
76
0
    LayoutDeviceIntPoint touchIntPoint = aEvent->mTouches[0]->mRefPoint;
77
0
    return nsPoint(touchIntPoint.x, touchIntPoint.y);
78
0
  }
79
80
  nsPoint GetMouseEventPosition(WidgetMouseEvent* aEvent) const override
81
0
  {
82
0
    // Return the device point directly.
83
0
    LayoutDeviceIntPoint mouseIntPoint = aEvent->AsGUIEvent()->mRefPoint;
84
0
    return nsPoint(mouseIntPoint.x, mouseIntPoint.y);
85
0
  }
86
87
  MockAccessibleCaretManager* GetMockAccessibleCaretManager()
88
0
  {
89
0
    return static_cast<MockAccessibleCaretManager*>(mManager.get());
90
0
  }
91
};
92
93
// Print the name of the state for debugging.
94
static ::std::ostream&
95
operator<<(::std::ostream& aOstream,
96
           const MockAccessibleCaretEventHub::State* aState)
97
0
{
98
0
  return aOstream << aState->Name();
99
0
}
100
101
class AccessibleCaretEventHubTester : public ::testing::Test
102
{
103
public:
104
  AccessibleCaretEventHubTester()
105
0
  {
106
0
    DefaultValue<nsresult>::Set(NS_OK);
107
0
    EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::NoActionState());
108
0
109
0
    // AccessibleCaretEventHub requires the caller to hold a ref to it. We just
110
0
    // add ref here for the sake of convenience.
111
0
    mHub.get()->AddRef();
112
0
  }
113
114
  ~AccessibleCaretEventHubTester() override
115
0
  {
116
0
    // Release the ref added in the constructor.
117
0
    mHub.get()->Release();
118
0
  }
119
120
  static UniquePtr<WidgetEvent> CreateMouseEvent(EventMessage aMessage,
121
                                                 nscoord aX,
122
                                                 nscoord aY)
123
0
  {
124
0
    auto event = MakeUnique<WidgetMouseEvent>(true, aMessage, nullptr,
125
0
                                              WidgetMouseEvent::eReal);
126
0
127
0
    event->button = WidgetMouseEvent::eLeftButton;
128
0
    event->mRefPoint = LayoutDeviceIntPoint(aX, aY);
129
0
130
0
    return std::move(event);
131
0
  }
132
133
  static UniquePtr<WidgetEvent> CreateMousePressEvent(nscoord aX, nscoord aY)
134
0
  {
135
0
    return CreateMouseEvent(eMouseDown, aX, aY);
136
0
  }
137
138
  static UniquePtr<WidgetEvent> CreateMouseMoveEvent(nscoord aX, nscoord aY)
139
0
  {
140
0
    return CreateMouseEvent(eMouseMove, aX, aY);
141
0
  }
142
143
  static UniquePtr<WidgetEvent> CreateMouseReleaseEvent(nscoord aX, nscoord aY)
144
0
  {
145
0
    return CreateMouseEvent(eMouseUp, aX, aY);
146
0
  }
147
148
  static UniquePtr<WidgetEvent> CreateLongTapEvent(nscoord aX, nscoord aY)
149
0
  {
150
0
    return CreateMouseEvent(eMouseLongTap, aX, aY);
151
0
  }
152
153
  static UniquePtr<WidgetEvent> CreateTouchEvent(EventMessage aMessage,
154
                                                 nscoord aX,
155
                                                 nscoord aY)
156
0
  {
157
0
    auto event = MakeUnique<WidgetTouchEvent>(true, aMessage, nullptr);
158
0
    int32_t identifier = 0;
159
0
    LayoutDeviceIntPoint point(aX, aY);
160
0
    LayoutDeviceIntPoint radius(19, 19);
161
0
    float rotationAngle = 0;
162
0
    float force = 1;
163
0
164
0
    RefPtr<dom::Touch> touch(
165
0
      new dom::Touch(identifier, point, radius, rotationAngle, force));
166
0
    event->mTouches.AppendElement(touch);
167
0
168
0
    return std::move(event);
169
0
  }
170
171
  static UniquePtr<WidgetEvent> CreateTouchStartEvent(nscoord aX, nscoord aY)
172
0
  {
173
0
    return CreateTouchEvent(eTouchStart, aX, aY);
174
0
  }
175
176
  static UniquePtr<WidgetEvent> CreateTouchMoveEvent(nscoord aX, nscoord aY)
177
0
  {
178
0
    return CreateTouchEvent(eTouchMove, aX, aY);
179
0
  }
180
181
  static UniquePtr<WidgetEvent> CreateTouchEndEvent(nscoord aX, nscoord aY)
182
0
  {
183
0
    return CreateTouchEvent(eTouchEnd, aX, aY);
184
0
  }
185
186
  static UniquePtr<WidgetEvent> CreateTouchCancelEvent(nscoord aX, nscoord aY)
187
0
  {
188
0
    return CreateTouchEvent(eTouchCancel, aX, aY);
189
0
  }
190
191
  static UniquePtr<WidgetEvent> CreateWheelEvent(EventMessage aMessage)
192
0
  {
193
0
    auto event = MakeUnique<WidgetWheelEvent>(true, aMessage, nullptr);
194
0
195
0
    return std::move(event);
196
0
  }
197
198
  MOZ_CAN_RUN_SCRIPT_BOUNDARY void TestAsyncPanZoomScroll();
199
200
  MOZ_CAN_RUN_SCRIPT_BOUNDARY
201
  void HandleEventAndCheckState(UniquePtr<WidgetEvent> aEvent,
202
                                MockAccessibleCaretEventHub::State* aExpectedState,
203
                                nsEventStatus aExpectedEventStatus)
204
0
  {
205
0
    nsEventStatus rv = mHub->HandleEvent(aEvent.get());
206
0
    EXPECT_EQ(mHub->GetState(), aExpectedState);
207
0
    EXPECT_EQ(rv, aExpectedEventStatus);
208
0
  }
209
210
  void CheckState(MockAccessibleCaretEventHub::State* aExpectedState)
211
0
  {
212
0
    EXPECT_EQ(mHub->GetState(), aExpectedState);
213
0
  }
214
215
  template<typename PressEventCreator, typename ReleaseEventCreator>
216
  MOZ_CAN_RUN_SCRIPT_BOUNDARY void TestPressReleaseOnNoCaret(
217
    PressEventCreator aPressEventCreator,
218
    ReleaseEventCreator aReleaseEventCreator);
219
220
  template<typename PressEventCreator, typename ReleaseEventCreator>
221
  MOZ_CAN_RUN_SCRIPT_BOUNDARY void TestPressReleaseOnCaret(
222
    PressEventCreator aPressEventCreator,
223
    ReleaseEventCreator aReleaseEventCreator);
224
225
  template<typename PressEventCreator,
226
           typename MoveEventCreator,
227
           typename ReleaseEventCreator>
228
  MOZ_CAN_RUN_SCRIPT_BOUNDARY void TestPressMoveReleaseOnNoCaret(
229
    PressEventCreator aPressEventCreator,
230
    MoveEventCreator aMoveEventCreator,
231
    ReleaseEventCreator aReleaseEventCreator);
232
233
  template<typename PressEventCreator,
234
           typename MoveEventCreator,
235
           typename ReleaseEventCreator>
236
  MOZ_CAN_RUN_SCRIPT_BOUNDARY void TestPressMoveReleaseOnCaret(
237
    PressEventCreator aPressEventCreator,
238
    MoveEventCreator aMoveEventCreator,
239
    ReleaseEventCreator aReleaseEventCreator);
240
241
  template<typename PressEventCreator, typename ReleaseEventCreator>
242
  MOZ_CAN_RUN_SCRIPT_BOUNDARY void TestLongTapWithSelectWordSuccessful(
243
    PressEventCreator aPressEventCreator,
244
    ReleaseEventCreator aReleaseEventCreator);
245
246
  template<typename PressEventCreator, typename ReleaseEventCreator>
247
  MOZ_CAN_RUN_SCRIPT_BOUNDARY void TestLongTapWithSelectWordFailed(
248
    PressEventCreator aPressEventCreator,
249
    ReleaseEventCreator aReleaseEventCreator);
250
251
  template<typename PressEventCreator,
252
           typename MoveEventCreator,
253
           typename ReleaseEventCreator>
254
  MOZ_CAN_RUN_SCRIPT_BOUNDARY void TestEventDrivenAsyncPanZoomScroll(
255
    PressEventCreator aPressEventCreator,
256
    MoveEventCreator aMoveEventCreator,
257
    ReleaseEventCreator aReleaseEventCreator);
258
259
  // Member variables
260
  RefPtr<MockAccessibleCaretEventHub> mHub{new MockAccessibleCaretEventHub()};
261
262
}; // class AccessibleCaretEventHubTester
263
264
TEST_F(AccessibleCaretEventHubTester, TestMousePressReleaseOnNoCaret)
265
MOZ_CAN_RUN_SCRIPT
266
0
{
267
0
  TestPressReleaseOnNoCaret(CreateMousePressEvent, CreateMouseReleaseEvent);
268
0
}
269
270
TEST_F(AccessibleCaretEventHubTester, TestTouchPressReleaseOnNoCaret)
271
MOZ_CAN_RUN_SCRIPT
272
0
{
273
0
  TestPressReleaseOnNoCaret(CreateTouchStartEvent, CreateTouchEndEvent);
274
0
}
275
276
template <typename PressEventCreator, typename ReleaseEventCreator>
277
void
278
AccessibleCaretEventHubTester::TestPressReleaseOnNoCaret(
279
  PressEventCreator aPressEventCreator,
280
  ReleaseEventCreator aReleaseEventCreator)
281
0
{
282
0
  EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), PressCaret(_, _))
283
0
    .WillOnce(Return(NS_ERROR_FAILURE));
284
0
285
0
  EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), ReleaseCaret()).Times(0);
286
0
287
0
  EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), TapCaret(_)).Times(0);
288
0
289
0
  HandleEventAndCheckState(aPressEventCreator(0, 0),
290
0
                           MockAccessibleCaretEventHub::PressNoCaretState(),
291
0
                           nsEventStatus_eIgnore);
292
0
293
0
  HandleEventAndCheckState(aReleaseEventCreator(0, 0),
294
0
                           MockAccessibleCaretEventHub::NoActionState(),
295
0
                           nsEventStatus_eIgnore);
296
0
}
297
298
TEST_F(AccessibleCaretEventHubTester, TestMousePressReleaseOnCaret)
299
MOZ_CAN_RUN_SCRIPT
300
0
{
301
0
  TestPressReleaseOnCaret(CreateMousePressEvent, CreateMouseReleaseEvent);
302
0
}
303
304
TEST_F(AccessibleCaretEventHubTester, TestTouchPressReleaseOnCaret)
305
MOZ_CAN_RUN_SCRIPT
306
0
{
307
0
  TestPressReleaseOnCaret(CreateTouchStartEvent, CreateTouchEndEvent);
308
0
}
309
310
template <typename PressEventCreator, typename ReleaseEventCreator>
311
void
312
AccessibleCaretEventHubTester::TestPressReleaseOnCaret(
313
  PressEventCreator aPressEventCreator,
314
  ReleaseEventCreator aReleaseEventCreator)
315
0
{
316
0
  {
317
0
    InSequence dummy;
318
0
319
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), PressCaret(_, _))
320
0
      .WillOnce(Return(NS_OK));
321
0
322
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), SelectWordOrShortcut(_))
323
0
      .Times(0);
324
0
325
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), ReleaseCaret());
326
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), TapCaret(_));
327
0
  }
328
0
329
0
  HandleEventAndCheckState(aPressEventCreator(0, 0),
330
0
                           MockAccessibleCaretEventHub::PressCaretState(),
331
0
                           nsEventStatus_eConsumeNoDefault);
332
0
333
0
  HandleEventAndCheckState(CreateLongTapEvent(0, 0),
334
0
                           MockAccessibleCaretEventHub::PressCaretState(),
335
0
                           nsEventStatus_eConsumeNoDefault);
336
0
337
0
  HandleEventAndCheckState(aReleaseEventCreator(0, 0),
338
0
                           MockAccessibleCaretEventHub::NoActionState(),
339
0
                           nsEventStatus_eConsumeNoDefault);
340
0
}
341
342
TEST_F(AccessibleCaretEventHubTester, TestMousePressMoveReleaseOnNoCaret)
343
MOZ_CAN_RUN_SCRIPT
344
0
{
345
0
  TestPressMoveReleaseOnNoCaret(CreateMousePressEvent, CreateMouseMoveEvent,
346
0
                                CreateMouseReleaseEvent);
347
0
}
348
349
TEST_F(AccessibleCaretEventHubTester, TestTouchPressMoveReleaseOnNoCaret)
350
MOZ_CAN_RUN_SCRIPT
351
0
{
352
0
  TestPressMoveReleaseOnNoCaret(CreateTouchStartEvent, CreateTouchMoveEvent,
353
0
                                CreateTouchEndEvent);
354
0
}
355
356
template <typename PressEventCreator, typename MoveEventCreator,
357
          typename ReleaseEventCreator>
358
void
359
AccessibleCaretEventHubTester::TestPressMoveReleaseOnNoCaret(
360
  PressEventCreator aPressEventCreator, MoveEventCreator aMoveEventCreator,
361
  ReleaseEventCreator aReleaseEventCreator)
362
0
{
363
0
  nscoord x0 = 0, y0 = 0;
364
0
  nscoord x1 = 100, y1 = 100;
365
0
  nscoord x2 = 300, y2 = 300;
366
0
  nscoord x3 = 400, y3 = 400;
367
0
368
0
  {
369
0
    InSequence dummy;
370
0
371
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), PressCaret(_, _))
372
0
      .WillOnce(Return(NS_ERROR_FAILURE));
373
0
374
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), DragCaret(_)).Times(0);
375
0
  }
376
0
377
0
  HandleEventAndCheckState(aPressEventCreator(x0, y0),
378
0
                           MockAccessibleCaretEventHub::PressNoCaretState(),
379
0
                           nsEventStatus_eIgnore);
380
0
381
0
  // A small move with the distance between (x0, y0) and (x1, y1) below the
382
0
  // tolerance value.
383
0
  HandleEventAndCheckState(aMoveEventCreator(x1, y1),
384
0
                           MockAccessibleCaretEventHub::PressNoCaretState(),
385
0
                           nsEventStatus_eIgnore);
386
0
387
0
  // A large move to simulate a dragging to select text since the distance
388
0
  // between (x0, y0) and (x2, y2) is above the tolerance value.
389
0
  HandleEventAndCheckState(aMoveEventCreator(x2, y2),
390
0
                           MockAccessibleCaretEventHub::NoActionState(),
391
0
                           nsEventStatus_eIgnore);
392
0
393
0
  HandleEventAndCheckState(aReleaseEventCreator(x3, y3),
394
0
                           MockAccessibleCaretEventHub::NoActionState(),
395
0
                           nsEventStatus_eIgnore);
396
0
}
397
398
TEST_F(AccessibleCaretEventHubTester, TestMousePressMoveReleaseOnCaret)
399
MOZ_CAN_RUN_SCRIPT
400
0
{
401
0
  TestPressMoveReleaseOnCaret(CreateMousePressEvent, CreateMouseMoveEvent,
402
0
                              CreateMouseReleaseEvent);
403
0
}
404
405
TEST_F(AccessibleCaretEventHubTester, TestTouchPressMoveReleaseOnCaret)
406
MOZ_CAN_RUN_SCRIPT
407
0
{
408
0
  TestPressMoveReleaseOnCaret(CreateTouchStartEvent, CreateTouchMoveEvent,
409
0
                              CreateTouchEndEvent);
410
0
}
411
412
template <typename PressEventCreator, typename MoveEventCreator,
413
          typename ReleaseEventCreator>
414
void
415
AccessibleCaretEventHubTester::TestPressMoveReleaseOnCaret(
416
  PressEventCreator aPressEventCreator, MoveEventCreator aMoveEventCreator,
417
  ReleaseEventCreator aReleaseEventCreator)
418
0
{
419
0
  nscoord x0 = 0, y0 = 0;
420
0
  nscoord x1 = 100, y1 = 100;
421
0
  nscoord x2 = 300, y2 = 300;
422
0
  nscoord x3 = 400, y3 = 400;
423
0
424
0
  {
425
0
    InSequence dummy;
426
0
427
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), PressCaret(_, _))
428
0
      .WillOnce(Return(NS_OK));
429
0
430
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), DragCaret(_))
431
0
      .Times(2) // two valid drag operations
432
0
      .WillRepeatedly(Return(NS_OK));
433
0
434
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), ReleaseCaret())
435
0
      .WillOnce(Return(NS_OK));
436
0
  }
437
0
438
0
  HandleEventAndCheckState(aPressEventCreator(x0, y0),
439
0
                           MockAccessibleCaretEventHub::PressCaretState(),
440
0
                           nsEventStatus_eConsumeNoDefault);
441
0
442
0
  // A small move with the distance between (x0, y0) and (x1, y1) below the
443
0
  // tolerance value.
444
0
  HandleEventAndCheckState(aMoveEventCreator(x1, y1),
445
0
                           MockAccessibleCaretEventHub::PressCaretState(),
446
0
                           nsEventStatus_eConsumeNoDefault);
447
0
448
0
  // A large move forms a valid drag since the distance between (x0, y0) and
449
0
  // (x2, y2) is above the tolerance value.
450
0
  HandleEventAndCheckState(aMoveEventCreator(x2, y2),
451
0
                           MockAccessibleCaretEventHub::DragCaretState(),
452
0
                           nsEventStatus_eConsumeNoDefault);
453
0
454
0
  // Also a valid drag since the distance between (x0, y0) and (x3, y3) above
455
0
  // the tolerance value even if the distance between (x2, y2) and (x3, y3) is
456
0
  // below the tolerance value.
457
0
  HandleEventAndCheckState(aMoveEventCreator(x3, y3),
458
0
                           MockAccessibleCaretEventHub::DragCaretState(),
459
0
                           nsEventStatus_eConsumeNoDefault);
460
0
461
0
  HandleEventAndCheckState(aReleaseEventCreator(x3, y3),
462
0
                           MockAccessibleCaretEventHub::NoActionState(),
463
0
                           nsEventStatus_eConsumeNoDefault);
464
0
}
465
466
TEST_F(AccessibleCaretEventHubTester,
467
       TestTouchStartMoveEndOnCaretWithTouchCancelIgnored)
468
MOZ_CAN_RUN_SCRIPT
469
0
{
470
0
  nscoord x0 = 0, y0 = 0;
471
0
  nscoord x1 = 100, y1 = 100;
472
0
  nscoord x2 = 300, y2 = 300;
473
0
  nscoord x3 = 400, y3 = 400;
474
0
475
0
  {
476
0
    InSequence dummy;
477
0
478
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), PressCaret(_, _))
479
0
      .WillOnce(Return(NS_OK));
480
0
481
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), DragCaret(_))
482
0
      .WillOnce(Return(NS_OK));
483
0
484
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), ReleaseCaret())
485
0
      .WillOnce(Return(NS_OK));
486
0
  }
487
0
488
0
  // All the eTouchCancel events should be ignored in this test.
489
0
490
0
  HandleEventAndCheckState(CreateTouchStartEvent(x0, y0),
491
0
                           MockAccessibleCaretEventHub::PressCaretState(),
492
0
                           nsEventStatus_eConsumeNoDefault);
493
0
494
0
  HandleEventAndCheckState(CreateTouchCancelEvent(x0, y0),
495
0
                           MockAccessibleCaretEventHub::PressCaretState(),
496
0
                           nsEventStatus_eIgnore);
497
0
498
0
  // A small move with the distance between (x0, y0) and (x1, y1) below the
499
0
  // tolerance value.
500
0
  HandleEventAndCheckState(CreateTouchMoveEvent(x1, y1),
501
0
                           MockAccessibleCaretEventHub::PressCaretState(),
502
0
                           nsEventStatus_eConsumeNoDefault);
503
0
504
0
  HandleEventAndCheckState(CreateTouchCancelEvent(x1, y1),
505
0
                           MockAccessibleCaretEventHub::PressCaretState(),
506
0
                           nsEventStatus_eIgnore);
507
0
508
0
  // A large move forms a valid drag since the distance between (x0, y0) and
509
0
  // (x2, y2) is above the tolerance value.
510
0
  HandleEventAndCheckState(CreateTouchMoveEvent(x2, y2),
511
0
                           MockAccessibleCaretEventHub::DragCaretState(),
512
0
                           nsEventStatus_eConsumeNoDefault);
513
0
514
0
  HandleEventAndCheckState(CreateTouchCancelEvent(x2, y2),
515
0
                           MockAccessibleCaretEventHub::DragCaretState(),
516
0
                           nsEventStatus_eIgnore);
517
0
518
0
  HandleEventAndCheckState(CreateTouchEndEvent(x3, y3),
519
0
                           MockAccessibleCaretEventHub::NoActionState(),
520
0
                           nsEventStatus_eConsumeNoDefault);
521
0
522
0
  HandleEventAndCheckState(CreateTouchCancelEvent(x3, y3),
523
0
                           MockAccessibleCaretEventHub::NoActionState(),
524
0
                           nsEventStatus_eIgnore);}
525
526
TEST_F(AccessibleCaretEventHubTester, TestMouseLongTapWithSelectWordSuccessful)
527
MOZ_CAN_RUN_SCRIPT
528
0
{
529
0
  TestLongTapWithSelectWordSuccessful(CreateMousePressEvent,
530
0
                                      CreateMouseReleaseEvent);
531
0
}
532
533
TEST_F(AccessibleCaretEventHubTester, TestTouchLongTapWithSelectWordSuccessful)
534
MOZ_CAN_RUN_SCRIPT
535
0
{
536
0
  TestLongTapWithSelectWordSuccessful(CreateTouchStartEvent,
537
0
                                      CreateTouchEndEvent);
538
0
}
539
540
template <typename PressEventCreator, typename ReleaseEventCreator>
541
void
542
AccessibleCaretEventHubTester::TestLongTapWithSelectWordSuccessful(
543
  PressEventCreator aPressEventCreator,
544
  ReleaseEventCreator aReleaseEventCreator)
545
0
{
546
0
  MockFunction<void(::std::string aCheckPointName)> check;
547
0
  {
548
0
    InSequence dummy;
549
0
550
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), PressCaret(_, _))
551
0
      .WillOnce(Return(NS_ERROR_FAILURE));
552
0
553
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), SelectWordOrShortcut(_))
554
0
      .WillOnce(Return(NS_OK));
555
0
556
0
    EXPECT_CALL(check, Call("longtap with scrolling"));
557
0
558
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), PressCaret(_, _))
559
0
      .WillOnce(Return(NS_ERROR_FAILURE));
560
0
561
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), SelectWordOrShortcut(_))
562
0
      .WillOnce(Return(NS_OK));
563
0
564
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollStart());
565
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollEnd());
566
0
  }
567
0
568
0
  // Test long tap without scrolling.
569
0
  HandleEventAndCheckState(aPressEventCreator(0, 0),
570
0
                           MockAccessibleCaretEventHub::PressNoCaretState(),
571
0
                           nsEventStatus_eIgnore);
572
0
573
0
  HandleEventAndCheckState(CreateLongTapEvent(0, 0),
574
0
                           MockAccessibleCaretEventHub::LongTapState(),
575
0
                           nsEventStatus_eIgnore);
576
0
577
0
  HandleEventAndCheckState(aReleaseEventCreator(0, 0),
578
0
                           MockAccessibleCaretEventHub::NoActionState(),
579
0
                           nsEventStatus_eIgnore);
580
0
581
0
  // On Fennec, after long tap, the script might scroll and zoom the input field
582
0
  // to the center of the screen to make typing easier before the user lifts the
583
0
  // finger.
584
0
  check.Call("longtap with scrolling");
585
0
586
0
  HandleEventAndCheckState(aPressEventCreator(1, 1),
587
0
                           MockAccessibleCaretEventHub::PressNoCaretState(),
588
0
                           nsEventStatus_eIgnore);
589
0
590
0
  HandleEventAndCheckState(CreateLongTapEvent(1, 1),
591
0
                           MockAccessibleCaretEventHub::LongTapState(),
592
0
                           nsEventStatus_eIgnore);
593
0
594
0
  mHub->AsyncPanZoomStarted();
595
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
596
0
597
0
  mHub->ScrollPositionChanged();
598
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
599
0
600
0
  mHub->AsyncPanZoomStopped();
601
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::NoActionState());
602
0
603
0
  HandleEventAndCheckState(aReleaseEventCreator(1, 1),
604
0
                           MockAccessibleCaretEventHub::NoActionState(),
605
0
                           nsEventStatus_eIgnore);
606
0
}
607
608
TEST_F(AccessibleCaretEventHubTester, TestMouseLongTapWithSelectWordFailed)
609
MOZ_CAN_RUN_SCRIPT
610
0
{
611
0
  TestLongTapWithSelectWordFailed(CreateMousePressEvent,
612
0
                                  CreateMouseReleaseEvent);
613
0
}
614
615
TEST_F(AccessibleCaretEventHubTester, TestTouchLongTapWithSelectWordFailed)
616
MOZ_CAN_RUN_SCRIPT
617
0
{
618
0
  TestLongTapWithSelectWordFailed(CreateTouchStartEvent,
619
0
                                  CreateTouchEndEvent);
620
0
}
621
622
template <typename PressEventCreator, typename ReleaseEventCreator>
623
void
624
AccessibleCaretEventHubTester::TestLongTapWithSelectWordFailed(
625
  PressEventCreator aPressEventCreator,
626
  ReleaseEventCreator aReleaseEventCreator)
627
0
{
628
0
  {
629
0
    InSequence dummy;
630
0
631
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), PressCaret(_, _))
632
0
      .WillOnce(Return(NS_ERROR_FAILURE));
633
0
634
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), SelectWordOrShortcut(_))
635
0
      .WillOnce(Return(NS_ERROR_FAILURE));
636
0
  }
637
0
638
0
  HandleEventAndCheckState(aPressEventCreator(0, 0),
639
0
                           MockAccessibleCaretEventHub::PressNoCaretState(),
640
0
                           nsEventStatus_eIgnore);
641
0
642
0
  HandleEventAndCheckState(CreateLongTapEvent(0, 0),
643
0
                           MockAccessibleCaretEventHub::LongTapState(),
644
0
                           nsEventStatus_eIgnore);
645
0
646
0
  HandleEventAndCheckState(aReleaseEventCreator(0, 0),
647
0
                           MockAccessibleCaretEventHub::NoActionState(),
648
0
                           nsEventStatus_eIgnore);
649
0
}
650
651
TEST_F(AccessibleCaretEventHubTester, TestTouchEventDrivenAsyncPanZoomScroll)
652
MOZ_CAN_RUN_SCRIPT
653
0
{
654
0
  TestEventDrivenAsyncPanZoomScroll(CreateTouchStartEvent, CreateTouchMoveEvent,
655
0
                                    CreateTouchEndEvent);
656
0
}
657
658
TEST_F(AccessibleCaretEventHubTester, TestMouseEventDrivenAsyncPanZoomScroll)
659
MOZ_CAN_RUN_SCRIPT
660
0
{
661
0
  TestEventDrivenAsyncPanZoomScroll(CreateMousePressEvent, CreateMouseMoveEvent,
662
0
                                    CreateMouseReleaseEvent);
663
0
}
664
665
template <typename PressEventCreator, typename MoveEventCreator,
666
          typename ReleaseEventCreator>
667
void
668
AccessibleCaretEventHubTester::TestEventDrivenAsyncPanZoomScroll(
669
  PressEventCreator aPressEventCreator, MoveEventCreator aMoveEventCreator,
670
  ReleaseEventCreator aReleaseEventCreator)
671
0
{
672
0
  MockFunction<void(::std::string aCheckPointName)> check;
673
0
  {
674
0
    InSequence dummy;
675
0
676
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), PressCaret(_, _))
677
0
      .WillOnce(Return(NS_ERROR_FAILURE));
678
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), DragCaret(_)).Times(0);
679
0
680
0
    EXPECT_CALL(check, Call("1"));
681
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollStart());
682
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollEnd());
683
0
684
0
    EXPECT_CALL(check, Call("2"));
685
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), PressCaret(_, _))
686
0
      .WillOnce(Return(NS_ERROR_FAILURE));
687
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), DragCaret(_)).Times(0);
688
0
689
0
    EXPECT_CALL(check, Call("3"));
690
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollStart());
691
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollEnd());
692
0
  }
693
0
694
0
  // Receive press event.
695
0
  HandleEventAndCheckState(aPressEventCreator(0, 0),
696
0
                           MockAccessibleCaretEventHub::PressNoCaretState(),
697
0
                           nsEventStatus_eIgnore);
698
0
699
0
  HandleEventAndCheckState(aMoveEventCreator(100, 100),
700
0
                           MockAccessibleCaretEventHub::PressNoCaretState(),
701
0
                           nsEventStatus_eIgnore);
702
0
703
0
  check.Call("1");
704
0
705
0
  // Event driven scroll started
706
0
  mHub->AsyncPanZoomStarted();
707
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
708
0
709
0
  HandleEventAndCheckState(aMoveEventCreator(160, 160),
710
0
                           MockAccessibleCaretEventHub::ScrollState(),
711
0
                           nsEventStatus_eIgnore);
712
0
713
0
  mHub->ScrollPositionChanged();
714
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
715
0
716
0
  // Event driven scroll ended
717
0
  mHub->AsyncPanZoomStopped();
718
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::NoActionState());
719
0
720
0
  HandleEventAndCheckState(aReleaseEventCreator(210, 210),
721
0
                           MockAccessibleCaretEventHub::NoActionState(),
722
0
                           nsEventStatus_eIgnore);
723
0
724
0
  check.Call("2");
725
0
726
0
  // Receive another press event.
727
0
  HandleEventAndCheckState(aPressEventCreator(220, 220),
728
0
                           MockAccessibleCaretEventHub::PressNoCaretState(),
729
0
                           nsEventStatus_eIgnore);
730
0
731
0
  HandleEventAndCheckState(aMoveEventCreator(230, 230),
732
0
                           MockAccessibleCaretEventHub::PressNoCaretState(),
733
0
                           nsEventStatus_eIgnore);
734
0
735
0
  check.Call("3");
736
0
737
0
  // Another APZ scroll started
738
0
  mHub->AsyncPanZoomStarted();
739
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
740
0
741
0
  mHub->ScrollPositionChanged();
742
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
743
0
744
0
  // Another APZ scroll ended
745
0
  mHub->AsyncPanZoomStopped();
746
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::NoActionState());
747
0
748
0
  HandleEventAndCheckState(aReleaseEventCreator(310, 310),
749
0
                           MockAccessibleCaretEventHub::NoActionState(),
750
0
                           nsEventStatus_eIgnore);
751
0
}
752
753
TEST_F(AccessibleCaretEventHubTester, TestAsyncPanZoomScroll) MOZ_CAN_RUN_SCRIPT
754
0
{
755
0
  TestAsyncPanZoomScroll();
756
0
}
757
758
void
759
AccessibleCaretEventHubTester::TestAsyncPanZoomScroll()
760
0
{
761
0
  MockFunction<void(::std::string aCheckPointName)> check;
762
0
  {
763
0
    InSequence dummy;
764
0
765
0
    EXPECT_CALL(check, Call("1"));
766
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollStart());
767
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(),
768
0
                OnScrollPositionChanged());
769
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollEnd());
770
0
771
0
    EXPECT_CALL(check, Call("2"));
772
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollStart());
773
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(),
774
0
                OnScrollPositionChanged());
775
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollEnd());
776
0
  }
777
0
778
0
  // First APZ scrolling.
779
0
  check.Call("1");
780
0
781
0
  mHub->AsyncPanZoomStarted();
782
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
783
0
784
0
  mHub->ScrollPositionChanged();
785
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
786
0
787
0
  mHub->AsyncPanZoomStopped();
788
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::NoActionState());
789
0
790
0
  // Second APZ scrolling.
791
0
  check.Call("2");
792
0
793
0
  mHub->AsyncPanZoomStarted();
794
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
795
0
796
0
  mHub->ScrollPositionChanged();
797
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
798
0
799
0
  mHub->AsyncPanZoomStopped();
800
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::NoActionState());
801
0
}
802
803
TEST_F(AccessibleCaretEventHubTester, TestAsyncPanZoomScrollStartedThenBlur)
804
MOZ_CAN_RUN_SCRIPT
805
0
{
806
0
  {
807
0
    InSequence dummy;
808
0
809
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollStart());
810
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollEnd()).Times(0);
811
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnBlur());
812
0
  }
813
0
814
0
  mHub->AsyncPanZoomStarted();
815
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
816
0
817
0
  mHub->ScrollPositionChanged();
818
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
819
0
820
0
  mHub->NotifyBlur(true);
821
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::NoActionState());
822
0
}
823
824
TEST_F(AccessibleCaretEventHubTester, TestAsyncPanZoomScrollEndedThenBlur)
825
MOZ_CAN_RUN_SCRIPT
826
0
{
827
0
  {
828
0
    InSequence dummy;
829
0
830
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollStart());
831
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnScrollEnd());
832
0
    EXPECT_CALL(*mHub->GetMockAccessibleCaretManager(), OnBlur());
833
0
  }
834
0
835
0
  mHub->AsyncPanZoomStarted();
836
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
837
0
838
0
  mHub->ScrollPositionChanged();
839
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::ScrollState());
840
0
841
0
  mHub->AsyncPanZoomStopped();
842
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::NoActionState());
843
0
844
0
  mHub->NotifyBlur(true);
845
0
  EXPECT_EQ(mHub->GetState(), MockAccessibleCaretEventHub::NoActionState());
846
0
}
847
848
} // namespace mozilla