// Copyright 2019 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

import 'dart:math' as math;

import 'package:flutter/material.dart';
import 'package:flutter/widgets.dart';
import 'package:flutter_test/flutter_test.dart';
import 'package:flutter/gestures.dart';

void main() {
  group('Horizontal', () {
    testWidgets('gets local corrdinates', (WidgetTester tester) async {
      int dragCancelCount = 0;
      final List<DragDownDetails> downDetails = <DragDownDetails>[];
      final List<DragEndDetails> endDetails = <DragEndDetails>[];
      final List<DragStartDetails> startDetails = <DragStartDetails>[];
      final List<DragUpdateDetails> updateDetails = <DragUpdateDetails>[];

      final Key redContainer = UniqueKey();
      await tester.pumpWidget(
        Center(
          child: GestureDetector(
            onHorizontalDragCancel: () {
              dragCancelCount++;
            },
            onHorizontalDragDown: (DragDownDetails details) {
              downDetails.add(details);
            },
            onHorizontalDragEnd: (DragEndDetails details) {
              endDetails.add(details);
            },
            onHorizontalDragStart: (DragStartDetails details) {
              startDetails.add(details);
            },
            onHorizontalDragUpdate: (DragUpdateDetails details) {
              updateDetails.add(details);
            },
            child: Container(
              key: redContainer,
              width: 100,
              height: 150,
              color: Colors.red,
            ),
          ),
        ),
      );

      await tester.drag(find.byKey(redContainer), const Offset(100, 0));
      expect(dragCancelCount, 0);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, hasLength(1));
      expect(startDetails.single.localPosition, const Offset(50, 75));
      expect(startDetails.single.globalPosition, const Offset(400, 300));
      expect(updateDetails.last.localPosition, const Offset(50 + 100.0, 75));
      expect(updateDetails.last.globalPosition, const Offset(400 + 100.0, 300));
      expect(
        updateDetails.fold(Offset.zero, (Offset offset, DragUpdateDetails details) => offset + details.delta),
        const Offset(100, 0),
      );
      expect(
        updateDetails.fold(0.0, (double offset, DragUpdateDetails details) => offset + details.primaryDelta),
        100.0,
      );
    });

    testWidgets('kTouchSlop is evaluated in the global coordinate space when scaled up', (WidgetTester tester) async {
      int dragCancelCount = 0;
      final List<DragDownDetails> downDetails = <DragDownDetails>[];
      final List<DragEndDetails> endDetails = <DragEndDetails>[];
      final List<DragStartDetails> startDetails = <DragStartDetails>[];
      final List<DragUpdateDetails> updateDetails = <DragUpdateDetails>[];

      final Key redContainer = UniqueKey();
      await tester.pumpWidget(
        Center(
          child: Transform.scale(
            scale: 2.0,
            child: GestureDetector(
              onHorizontalDragCancel: () {
                dragCancelCount++;
              },
              onHorizontalDragDown: (DragDownDetails details) {
                downDetails.add(details);
              },
              onHorizontalDragEnd: (DragEndDetails details) {
                endDetails.add(details);
              },
              onHorizontalDragStart: (DragStartDetails details) {
                startDetails.add(details);
              },
              onHorizontalDragUpdate: (DragUpdateDetails details) {
                updateDetails.add(details);
              },
              onTap: () {
                // Competing gesture detector.
              },
              child: Container(
                key: redContainer,
                width: 100,
                height: 150,
                color: Colors.red,
              ),
            ),
          ),
        ),
      );

      // Move just above kTouchSlop should recognize drag.
      await tester.drag(find.byKey(redContainer), const Offset(kTouchSlop + 1, 0));

      expect(dragCancelCount, 0);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, hasLength(1));
      expect(startDetails.single.localPosition, const Offset(50 + (kTouchSlop + 1) / 2, 75));
      expect(startDetails.single.globalPosition, const Offset(400 + (kTouchSlop + 1), 300));
      expect(updateDetails, isEmpty);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();

      // Move just below kTouchSlop does not recognize drag.
      await tester.drag(find.byKey(redContainer), const Offset(kTouchSlop - 1, 0));
      expect(dragCancelCount, 1);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, isEmpty);
      expect(startDetails, isEmpty);
      expect(updateDetails, isEmpty);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();

      // Move in two separate movements
      final TestGesture gesture = await tester.startGesture(tester.getCenter(find.byKey(redContainer)));
      await gesture.moveBy(const Offset(kTouchSlop + 1, 30));
      await gesture.moveBy(const Offset(100, 10));
      await gesture.up();

      expect(dragCancelCount, 0);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, hasLength(1));
      expect(startDetails.single.localPosition, const Offset(50 + (kTouchSlop + 1) / 2, 75.0 + 30.0 / 2));
      expect(startDetails.single.globalPosition, const Offset(400 + (kTouchSlop + 1), 300 + 30.0));
      expect(updateDetails.single.localPosition, startDetails.single.localPosition + const Offset(100.0 / 2, 10 / 2));
      expect(updateDetails.single.globalPosition, startDetails.single.globalPosition + const Offset(100.0, 10.0));
      expect(updateDetails.single.delta, const Offset(100.0 / 2, 0.0));
      expect(updateDetails.single.primaryDelta, 100.0 / 2);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();
    });

    testWidgets('kTouchSlop is evaluated in the global coordinate space when scaled down', (WidgetTester tester) async {
      int dragCancelCount = 0;
      final List<DragDownDetails> downDetails = <DragDownDetails>[];
      final List<DragEndDetails> endDetails = <DragEndDetails>[];
      final List<DragStartDetails> startDetails = <DragStartDetails>[];
      final List<DragUpdateDetails> updateDetails = <DragUpdateDetails>[];

      final Key redContainer = UniqueKey();
      await tester.pumpWidget(
        Center(
          child: Transform.scale(
            scale: 0.5,
            child: GestureDetector(
              onHorizontalDragCancel: () {
                dragCancelCount++;
              },
              onHorizontalDragDown: (DragDownDetails details) {
                downDetails.add(details);
              },
              onHorizontalDragEnd: (DragEndDetails details) {
                endDetails.add(details);
              },
              onHorizontalDragStart: (DragStartDetails details) {
                startDetails.add(details);
              },
              onHorizontalDragUpdate: (DragUpdateDetails details) {
                updateDetails.add(details);
              },
              onTap: () {
                // Competing gesture detector.
              },
              child: Container(
                key: redContainer,
                width: 100,
                height: 150,
                color: Colors.red,
              ),
            ),
          ),
        ),
      );

      // Move just above kTouchSlop should recognize drag.
      await tester.drag(find.byKey(redContainer), const Offset(kTouchSlop + 1, 0));

      expect(dragCancelCount, 0);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, hasLength(1));
      expect(startDetails.single.localPosition, const Offset(50 + (kTouchSlop + 1) * 2, 75));
      expect(startDetails.single.globalPosition, const Offset(400 + (kTouchSlop + 1), 300));
      expect(updateDetails, isEmpty);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();

      // Move just below kTouchSlop does not recognize drag.
      await tester.drag(find.byKey(redContainer), const Offset(kTouchSlop - 1, 0));
      expect(dragCancelCount, 1);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, isEmpty);
      expect(startDetails, isEmpty);
      expect(updateDetails, isEmpty);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();

      // Move in two separate movements
      final TestGesture gesture = await tester.startGesture(tester.getCenter(find.byKey(redContainer)));
      await gesture.moveBy(const Offset(kTouchSlop + 1, 30));
      await gesture.moveBy(const Offset(100, 10));
      await gesture.up();

      expect(dragCancelCount, 0);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, hasLength(1));
      expect(startDetails.single.localPosition, const Offset(50 + (kTouchSlop + 1) * 2, 75.0 + 30.0 * 2));
      expect(startDetails.single.globalPosition, const Offset(400 + (kTouchSlop + 1), 300 + 30.0));
      expect(updateDetails.single.localPosition, startDetails.single.localPosition + const Offset(100.0 * 2, 10.0 * 2.0));
      expect(updateDetails.single.globalPosition, startDetails.single.globalPosition + const Offset(100.0, 10.0));
      expect(updateDetails.single.delta, const Offset(100.0 * 2.0, 0.0));
      expect(updateDetails.single.primaryDelta, 100.0 * 2);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();
    });

    testWidgets('kTouchSlop is evaluated in the global coordinate space when roateted 45 degrees', (WidgetTester tester) async {
      int dragCancelCount = 0;
      final List<DragDownDetails> downDetails = <DragDownDetails>[];
      final List<DragEndDetails> endDetails = <DragEndDetails>[];
      final List<DragStartDetails> startDetails = <DragStartDetails>[];
      final List<DragUpdateDetails> updateDetails = <DragUpdateDetails>[];

      final Key redContainer = UniqueKey();
      await tester.pumpWidget(
        Center(
          child: Transform.rotate(
            angle: math.pi / 4,
            child: GestureDetector(
              onHorizontalDragCancel: () {
                dragCancelCount++;
              },
              onHorizontalDragDown: (DragDownDetails details) {
                downDetails.add(details);
              },
              onHorizontalDragEnd: (DragEndDetails details) {
                endDetails.add(details);
              },
              onHorizontalDragStart: (DragStartDetails details) {
                startDetails.add(details);
              },
              onHorizontalDragUpdate: (DragUpdateDetails details) {
                updateDetails.add(details);
              },
              onTap: () {
                // Competing gesture detector.
              },
              child: Container(
                key: redContainer,
                width: 100,
                height: 150,
                color: Colors.red,
              ),
            ),
          ),
        ),
      );

      // Move just below kTouchSlop should not recognize drag.
      const Offset moveBy1 = Offset(kTouchSlop/ 2, kTouchSlop / 2);
      expect(moveBy1.distance, lessThan(kTouchSlop));
      await tester.drag(find.byKey(redContainer), moveBy1);
      expect(dragCancelCount, 1);
      expect(downDetails.single.localPosition, within(distance: 0.0001, from: const Offset(50, 75)));
      expect(downDetails.single.globalPosition, within(distance: 0.0001, from: const Offset(400, 300)));
      expect(endDetails, isEmpty);
      expect(startDetails, isEmpty);
      expect(updateDetails, isEmpty);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();

      // Move above kTouchSlop recognizes drag.
      final TestGesture gesture = await tester.startGesture(tester.getCenter(find.byKey(redContainer)));
      await gesture.moveBy(const Offset(kTouchSlop, kTouchSlop));
      await gesture.moveBy(const Offset(3, 4));
      await gesture.up();

      expect(dragCancelCount, 0);
      expect(downDetails.single.localPosition,  within(distance: 0.0001, from: const Offset(50, 75)));
      expect(downDetails.single.globalPosition,  within(distance: 0.0001, from: const Offset(400, 300)));
      expect(endDetails, hasLength(1));
      expect(startDetails, hasLength(1));
      expect(updateDetails.single.globalPosition, within(distance: 0.0001, from: const Offset(400 + kTouchSlop + 3, 300 + kTouchSlop + 4)));
      expect(updateDetails.single.delta, within(distance: 0.1, from: const Offset(5, 0.0))); // sqrt(3^2 + 4^2)
      expect(updateDetails.single.primaryDelta, within(distance: 0.1, from: 5.0)); // sqrt(3^2 + 4^2)
    });
  });

  group('Vertical', () {
    testWidgets('gets local corrdinates', (WidgetTester tester) async {
      int dragCancelCount = 0;
      final List<DragDownDetails> downDetails = <DragDownDetails>[];
      final List<DragEndDetails> endDetails = <DragEndDetails>[];
      final List<DragStartDetails> startDetails = <DragStartDetails>[];
      final List<DragUpdateDetails> updateDetails = <DragUpdateDetails>[];

      final Key redContainer = UniqueKey();
      await tester.pumpWidget(
        Center(
          child: GestureDetector(
            onVerticalDragCancel: () {
              dragCancelCount++;
            },
            onVerticalDragDown: (DragDownDetails details) {
              downDetails.add(details);
            },
            onVerticalDragEnd: (DragEndDetails details) {
              endDetails.add(details);
            },
            onVerticalDragStart: (DragStartDetails details) {
              startDetails.add(details);
            },
            onVerticalDragUpdate: (DragUpdateDetails details) {
              updateDetails.add(details);
            },
            child: Container(
              key: redContainer,
              width: 100,
              height: 150,
              color: Colors.red,
            ),
          ),
        ),
      );

      await tester.drag(find.byKey(redContainer), const Offset(0, 100));
      expect(dragCancelCount, 0);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, hasLength(1));
      expect(startDetails.single.localPosition, const Offset(50, 75));
      expect(startDetails.single.globalPosition, const Offset(400, 300));
      expect(updateDetails.last.localPosition, const Offset(50, 75 + 100.0));
      expect(updateDetails.last.globalPosition, const Offset(400, 300 + 100.0));
      expect(
        updateDetails.fold(Offset.zero, (Offset offset, DragUpdateDetails details) => offset + details.delta),
        const Offset(0, 100),
      );
      expect(
        updateDetails.fold(0.0, (double offset, DragUpdateDetails details) => offset + details.primaryDelta),
        100.0,
      );
    });

    testWidgets('kTouchSlop is evaluated in the global coordinate space when scaled up', (WidgetTester tester) async {
      int dragCancelCount = 0;
      final List<DragDownDetails> downDetails = <DragDownDetails>[];
      final List<DragEndDetails> endDetails = <DragEndDetails>[];
      final List<DragStartDetails> startDetails = <DragStartDetails>[];
      final List<DragUpdateDetails> updateDetails = <DragUpdateDetails>[];

      final Key redContainer = UniqueKey();
      await tester.pumpWidget(
        Center(
          child: Transform.scale(
            scale: 2.0,
            child: GestureDetector(
              onVerticalDragCancel: () {
                dragCancelCount++;
              },
              onVerticalDragDown: (DragDownDetails details) {
                downDetails.add(details);
              },
              onVerticalDragEnd: (DragEndDetails details) {
                endDetails.add(details);
              },
              onVerticalDragStart: (DragStartDetails details) {
                startDetails.add(details);
              },
              onVerticalDragUpdate: (DragUpdateDetails details) {
                updateDetails.add(details);
              },
              onTap: () {
                // Competing gesture detector.
              },
              child: Container(
                key: redContainer,
                width: 100,
                height: 150,
                color: Colors.red,
              ),
            ),
          ),
        ),
      );

      // Move just above kTouchSlop should recognize drag.
      await tester.drag(find.byKey(redContainer), const Offset(0, kTouchSlop + 1));

      expect(dragCancelCount, 0);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, hasLength(1));
      expect(startDetails.single.localPosition, const Offset(50, 75 + (kTouchSlop + 1) / 2));
      expect(startDetails.single.globalPosition, const Offset(400, 300 + (kTouchSlop + 1)));
      expect(updateDetails, isEmpty);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();

      // Move just below kTouchSlop does not recognize drag.
      await tester.drag(find.byKey(redContainer), const Offset(0, kTouchSlop - 1));
      expect(dragCancelCount, 1);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, isEmpty);
      expect(startDetails, isEmpty);
      expect(updateDetails, isEmpty);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();

      // Move in two separate movements
      final TestGesture gesture = await tester.startGesture(tester.getCenter(find.byKey(redContainer)));
      await gesture.moveBy(const Offset(30, kTouchSlop + 1));
      await gesture.moveBy(const Offset(10, 100));
      await gesture.up();

      expect(dragCancelCount, 0);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, hasLength(1));
      expect(startDetails.single.localPosition, const Offset(50 + 30.0 / 2, 75.0 + (kTouchSlop + 1) / 2));
      expect(startDetails.single.globalPosition, const Offset(400 + 30.0, 300 + (kTouchSlop + 1)));
      expect(updateDetails.single.localPosition, startDetails.single.localPosition + const Offset(10.0 / 2, 100.0 / 2));
      expect(updateDetails.single.globalPosition, startDetails.single.globalPosition + const Offset(10.0, 100.0));
      expect(updateDetails.single.delta, const Offset(0.0, 100.0 / 2));
      expect(updateDetails.single.primaryDelta, 100.0 / 2);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();
    });

    testWidgets('kTouchSlop is evaluated in the global coordinate space when scaled down', (WidgetTester tester) async {
      int dragCancelCount = 0;
      final List<DragDownDetails> downDetails = <DragDownDetails>[];
      final List<DragEndDetails> endDetails = <DragEndDetails>[];
      final List<DragStartDetails> startDetails = <DragStartDetails>[];
      final List<DragUpdateDetails> updateDetails = <DragUpdateDetails>[];

      final Key redContainer = UniqueKey();
      await tester.pumpWidget(
        Center(
          child: Transform.scale(
            scale: 0.5,
            child: GestureDetector(
              onVerticalDragCancel: () {
                dragCancelCount++;
              },
              onVerticalDragDown: (DragDownDetails details) {
                downDetails.add(details);
              },
              onVerticalDragEnd: (DragEndDetails details) {
                endDetails.add(details);
              },
              onVerticalDragStart: (DragStartDetails details) {
                startDetails.add(details);
              },
              onVerticalDragUpdate: (DragUpdateDetails details) {
                updateDetails.add(details);
              },
              onTap: () {
                // Competing gesture detector.
              },
              child: Container(
                key: redContainer,
                width: 100,
                height: 150,
                color: Colors.red,
              ),
            ),
          ),
        ),
      );

      // Move just above kTouchSlop should recognize drag.
      await tester.drag(find.byKey(redContainer), const Offset(0, kTouchSlop + 1));

      expect(dragCancelCount, 0);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, hasLength(1));
      expect(startDetails.single.localPosition, const Offset(50, 75 + (kTouchSlop + 1) * 2));
      expect(startDetails.single.globalPosition, const Offset(400, 300 + (kTouchSlop + 1)));
      expect(updateDetails, isEmpty);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();

      // Move just below kTouchSlop does not recognize drag.
      await tester.drag(find.byKey(redContainer), const Offset(0, kTouchSlop - 1));
      expect(dragCancelCount, 1);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, isEmpty);
      expect(startDetails, isEmpty);
      expect(updateDetails, isEmpty);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();

      // Move in two separate movements
      final TestGesture gesture = await tester.startGesture(tester.getCenter(find.byKey(redContainer)));
      await gesture.moveBy(const Offset(30, kTouchSlop + 1));
      await gesture.moveBy(const Offset(10, 100));
      await gesture.up();

      expect(dragCancelCount, 0);
      expect(downDetails.single.localPosition, const Offset(50, 75));
      expect(downDetails.single.globalPosition, const Offset(400, 300));
      expect(endDetails, hasLength(1));
      expect(startDetails.single.localPosition, const Offset(50 + 30.0 * 2, 75.0 + (kTouchSlop + 1) * 2));
      expect(startDetails.single.globalPosition, const Offset(400 + 30.0, 300 + (kTouchSlop + 1)));
      expect(updateDetails.single.localPosition, startDetails.single.localPosition + const Offset(10.0 * 2, 100.0 * 2.0));
      expect(updateDetails.single.globalPosition, startDetails.single.globalPosition + const Offset(10.0, 100.0));
      expect(updateDetails.single.delta, const Offset(0.0, 100.0 * 2.0));
      expect(updateDetails.single.primaryDelta, 100.0 * 2);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();
    });

    testWidgets('kTouchSlop is evaluated in the global coordinate space when roateted 45 degrees', (WidgetTester tester) async {
      int dragCancelCount = 0;
      final List<DragDownDetails> downDetails = <DragDownDetails>[];
      final List<DragEndDetails> endDetails = <DragEndDetails>[];
      final List<DragStartDetails> startDetails = <DragStartDetails>[];
      final List<DragUpdateDetails> updateDetails = <DragUpdateDetails>[];

      final Key redContainer = UniqueKey();
      await tester.pumpWidget(
        Center(
          child: Transform.rotate(
            angle: math.pi / 4,
            child: GestureDetector(
              onVerticalDragCancel: () {
                dragCancelCount++;
              },
              onVerticalDragDown: (DragDownDetails details) {
                downDetails.add(details);
              },
              onVerticalDragEnd: (DragEndDetails details) {
                endDetails.add(details);
              },
              onVerticalDragStart: (DragStartDetails details) {
                startDetails.add(details);
              },
              onVerticalDragUpdate: (DragUpdateDetails details) {
                updateDetails.add(details);
              },
              onTap: () {
                // Competing gesture detector.
              },
              child: Container(
                key: redContainer,
                width: 100,
                height: 150,
                color: Colors.red,
              ),
            ),
          ),
        ),
      );

      // Move just below kTouchSlop should not recognize drag.
      const Offset moveBy1 = Offset(kTouchSlop/ 2, kTouchSlop / 2);
      expect(moveBy1.distance, lessThan(kTouchSlop));
      await tester.drag(find.byKey(redContainer), moveBy1);
      expect(dragCancelCount, 1);
      expect(downDetails.single.localPosition, within(distance: 0.0001, from: const Offset(50, 75)));
      expect(downDetails.single.globalPosition, within(distance: 0.0001, from: const Offset(400, 300)));
      expect(endDetails, isEmpty);
      expect(startDetails, isEmpty);
      expect(updateDetails, isEmpty);

      dragCancelCount = 0;
      downDetails.clear();
      endDetails.clear();
      startDetails.clear();
      updateDetails.clear();

      // Move above kTouchSlop recognizes drag.
      final TestGesture gesture = await tester.startGesture(tester.getCenter(find.byKey(redContainer)));
      await gesture.moveBy(const Offset(kTouchSlop, kTouchSlop));
      await gesture.moveBy(const Offset(-4, 3));
      await gesture.up();

      expect(dragCancelCount, 0);
      expect(downDetails.single.localPosition,  within(distance: 0.0001, from: const Offset(50, 75)));
      expect(downDetails.single.globalPosition,  within(distance: 0.0001, from: const Offset(400, 300)));
      expect(endDetails, hasLength(1));
      expect(startDetails, hasLength(1));
      expect(updateDetails.single.globalPosition, within(distance: 0.0001, from: const Offset(400 + kTouchSlop - 4, 300 + kTouchSlop + 3)));
      expect(updateDetails.single.delta, within(distance: 0.1, from: const Offset(0.0, 5.0))); // sqrt(3^2 + 4^2)
      expect(updateDetails.single.primaryDelta, within(distance: 0.1, from: 5.0)); // sqrt(3^2 + 4^2)
    });
  });
}
