Files
plezy/test/services/gamepad_duplicate_input_guard_test.dart
T
2026-07-11 03:23:40 +02:00

89 lines
3.3 KiB
Dart

import 'package:flutter/services.dart';
import 'package:flutter_test/flutter_test.dart';
import 'package:plezy/services/gamepad_service.dart';
void main() {
group('GamepadDuplicateInputGuard', () {
late DateTime now;
late GamepadDuplicateInputGuard guard;
setUp(() {
now = DateTime(2026, 4, 26, 12);
guard = GamepadDuplicateInputGuard(now: () => now, suppressionWindow: const Duration(milliseconds: 100));
});
test('suppresses a matching D-pad event after a native arrow key', () {
guard.handleNativeKeyEvent(_keyDown(LogicalKeyboardKey.arrowRight));
expect(guard.shouldSuppressSyntheticKey(LogicalKeyboardKey.arrowRight), isTrue);
});
test('does not suppress D-pad input when no native key was seen', () {
expect(guard.shouldSuppressSyntheticKey(LogicalKeyboardKey.arrowRight), isFalse);
});
test('suppresses gamepad A while native enter is down and just after release', () {
guard.handleNativeKeyEvent(_keyDown(LogicalKeyboardKey.enter));
expect(guard.shouldSuppressSyntheticKey(LogicalKeyboardKey.enter), isTrue);
guard.handleNativeKeyEvent(_keyUp(LogicalKeyboardKey.enter));
now = now.add(const Duration(milliseconds: 50));
expect(guard.shouldSuppressSyntheticKey(LogicalKeyboardKey.enter), isTrue);
});
test('suppression expires after the debounce window', () {
guard.handleNativeKeyEvent(_keyDown(LogicalKeyboardKey.arrowRight));
guard.handleNativeKeyEvent(_keyUp(LogicalKeyboardKey.arrowRight));
now = now.add(const Duration(milliseconds: 101));
expect(guard.shouldSuppressSyntheticKey(LogicalKeyboardKey.arrowRight), isFalse);
});
test('unrelated native keys do not suppress controller input', () {
guard.handleNativeKeyEvent(_keyDown(LogicalKeyboardKey.space));
expect(guard.shouldSuppressSyntheticKey(LogicalKeyboardKey.arrowRight), isFalse);
expect(guard.shouldSuppressSyntheticKey(LogicalKeyboardKey.enter), isFalse);
});
test('uses aliases for Steam Input mapped context menu and back keys', () {
guard.handleNativeKeyEvent(_keyDown(LogicalKeyboardKey.contextMenu));
expect(guard.shouldSuppressSyntheticKey(LogicalKeyboardKey.gameButtonX), isTrue);
guard.clear();
guard.handleNativeKeyEvent(_keyDown(LogicalKeyboardKey.browserBack));
expect(guard.shouldSuppressSyntheticKey(LogicalKeyboardKey.gameButtonB), isTrue);
});
});
}
KeyDownEvent _keyDown(LogicalKeyboardKey logicalKey) {
return KeyDownEvent(
physicalKey: _physicalKeyFor(logicalKey),
logicalKey: logicalKey,
timeStamp: const Duration(milliseconds: 1),
);
}
KeyUpEvent _keyUp(LogicalKeyboardKey logicalKey) {
return KeyUpEvent(
physicalKey: _physicalKeyFor(logicalKey),
logicalKey: logicalKey,
timeStamp: const Duration(milliseconds: 1),
);
}
PhysicalKeyboardKey _physicalKeyFor(LogicalKeyboardKey logicalKey) {
if (logicalKey == LogicalKeyboardKey.arrowRight) return PhysicalKeyboardKey.arrowRight;
if (logicalKey == LogicalKeyboardKey.enter) return PhysicalKeyboardKey.enter;
if (logicalKey == LogicalKeyboardKey.space) return PhysicalKeyboardKey.space;
if (logicalKey == LogicalKeyboardKey.contextMenu) return PhysicalKeyboardKey.contextMenu;
if (logicalKey == LogicalKeyboardKey.browserBack) return PhysicalKeyboardKey.browserBack;
return PhysicalKeyboardKey.enter;
}