diff --git a/lib/common/widgets/gesture/image_horizontal_drag_gesture_recognizer.dart b/lib/common/widgets/gesture/image_horizontal_drag_gesture_recognizer.dart index f4170ab94..605be20c8 100644 --- a/lib/common/widgets/gesture/image_horizontal_drag_gesture_recognizer.dart +++ b/lib/common/widgets/gesture/image_horizontal_drag_gesture_recognizer.dart @@ -1,87 +1,89 @@ import 'package:PiliPlus/common/widgets/gesture/horizontal_drag_gesture_recognizer.dart'; -import 'package:PiliPlus/utils/platform_utils.dart'; import 'package:flutter/gestures.dart'; -mixin ImageGestureRecognizerMixin on GestureRecognizer { - int? _pointer; - - @override - void addPointer(PointerDownEvent event, {bool isPointerAllowed = true}) { - if (_pointer == event.pointer) { - return; - } - _pointer = event.pointer; - if (isPointerAllowed) { - super.addPointer(event); - } - } -} - class ImageHorizontalDragGestureRecognizer - extends CustomHorizontalDragGestureRecognizer - with ImageGestureRecognizerMixin { + extends CustomHorizontalDragGestureRecognizer { ImageHorizontalDragGestureRecognizer({ super.debugOwner, super.supportedDevices, super.allowedButtonsFilter, }); - static final double _touchSlop = PlatformUtils.isDesktop - ? kPrecisePointerHitSlop - : 3.0; + int? _pointer; - @override - DeviceGestureSettings get gestureSettings => _gestureSettings; - final _gestureSettings = DeviceGestureSettings(touchSlop: _touchSlop); + bool _reset = true; + bool _hasAcceptedOrRejected = false; bool isAtLeftEdge = false; bool isAtRightEdge = false; + @override + void addPointer(PointerDownEvent event, {bool isPointerAllowed = true}) { + if (_pointer == event.pointer) { + return; + } + if (!_reset && + _pointer != event.pointer && + isPointerAllowed && + !_hasAcceptedOrRejected) { + rejectGesture(_pointer!); + _pointer = event.pointer; + return; + } + _reset = false; + _pointer = event.pointer; + if (isPointerAllowed) { + super.addPointer(event); + } + } + void setAtBothEdges() { isAtLeftEdge = isAtRightEdge = true; } bool _isEdgeAllowed(double dx) { - if ((initialPosition!.dx - dx).abs() < _touchSlop) return true; if (isAtLeftEdge) { if (isAtRightEdge) { - return _hasAcceptedOrChecked = true; + return true; } - _hasAcceptedOrChecked = true; return initialPosition!.dx < dx; } else if (isAtRightEdge) { - _hasAcceptedOrChecked = true; return initialPosition!.dx > dx; } return true; } - @override - void handleEvent(PointerEvent event) { - if (!_hasAcceptedOrChecked && - event is PointerMoveEvent && - _pointer == event.pointer) { - if (!_isEdgeAllowed(event.position.dx)) { - rejectGesture(event.pointer); - return; - } - } - super.handleEvent(event); - } - - bool _hasAcceptedOrChecked = false; - @override void acceptGesture(int pointer) { - _hasAcceptedOrChecked = true; + _hasAcceptedOrRejected = true; super.acceptGesture(pointer); } + @override + void rejectGesture(int pointer) { + _hasAcceptedOrRejected = true; + super.rejectGesture(pointer); + } + @override void stopTrackingPointer(int pointer) { - _hasAcceptedOrChecked = false; + _reset = true; + _hasAcceptedOrRejected = false; + isAtLeftEdge = false; isAtRightEdge = false; super.stopTrackingPointer(pointer); } + + @override + bool hasSufficientGlobalDistanceToAccept( + PointerDeviceKind pointerDeviceKind, + double? deviceTouchSlop, + ) { + return super.hasSufficientGlobalDistanceToAccept( + pointerDeviceKind, + deviceTouchSlop, + ) && + _isEdgeAllowed(lastPosition.global.dx); + } }