From 6f44e0514bd01fe7df2a16a85aff0fa62f111b84 Mon Sep 17 00:00:00 2001 From: Erick Zanardo Date: Thu, 31 Oct 2019 20:05:23 -0300 Subject: [PATCH] Fixing gestures conflicts and adding a gestures example --- doc/examples/gestures/.gitignore | 72 +++++++++++++++++++ doc/examples/gestures/.metadata | 10 +++ doc/examples/gestures/README.md | 3 + doc/examples/gestures/lib/main.dart | 50 +++++++++++++ doc/examples/gestures/pubspec.yaml | 16 +++++ lib/game.dart | 105 ++++++++++++++++++---------- 6 files changed, 221 insertions(+), 35 deletions(-) create mode 100644 doc/examples/gestures/.gitignore create mode 100644 doc/examples/gestures/.metadata create mode 100644 doc/examples/gestures/README.md create mode 100644 doc/examples/gestures/lib/main.dart create mode 100644 doc/examples/gestures/pubspec.yaml diff --git a/doc/examples/gestures/.gitignore b/doc/examples/gestures/.gitignore new file mode 100644 index 000000000..ac4a90645 --- /dev/null +++ b/doc/examples/gestures/.gitignore @@ -0,0 +1,72 @@ +# Miscellaneous +*.class +*.log +*.pyc +*.swp +.DS_Store +.atom/ +.buildlog/ +.history +.svn/ + +# IntelliJ related +*.iml +*.ipr +*.iws +.idea/ + +# The .vscode folder contains launch configuration and tasks you configure in +# VS Code which you may wish to be included in version control, so this line +# is commented out by default. +#.vscode/ + +# Flutter/Dart/Pub related +**/doc/api/ +.dart_tool/ +.flutter-plugins +.packages +.pub-cache/ +.pub/ +/build/ + +# Android related +**/android/**/gradle-wrapper.jar +**/android/.gradle +**/android/captures/ +**/android/gradlew +**/android/gradlew.bat +**/android/local.properties +**/android/**/GeneratedPluginRegistrant.java + +# iOS/XCode related +**/ios/**/*.mode1v3 +**/ios/**/*.mode2v3 +**/ios/**/*.moved-aside +**/ios/**/*.pbxuser +**/ios/**/*.perspectivev3 +**/ios/**/*sync/ +**/ios/**/.sconsign.dblite +**/ios/**/.tags* +**/ios/**/.vagrant/ +**/ios/**/DerivedData/ +**/ios/**/Icon? +**/ios/**/Pods/ +**/ios/**/.symlinks/ +**/ios/**/profile +**/ios/**/xcuserdata +**/ios/.generated/ +**/ios/Flutter/App.framework +**/ios/Flutter/Flutter.framework +**/ios/Flutter/Generated.xcconfig +**/ios/Flutter/app.flx +**/ios/Flutter/app.zip +**/ios/Flutter/flutter_assets/ +**/ios/ServiceDefinitions.json +**/ios/Runner/GeneratedPluginRegistrant.* + +# Exceptions to above rules. +!**/ios/**/default.mode1v3 +!**/ios/**/default.mode2v3 +!**/ios/**/default.pbxuser +!**/ios/**/default.perspectivev3 +!/packages/flutter_tools/test/data/dart_dependencies_test/**/.packages diff --git a/doc/examples/gestures/.metadata b/doc/examples/gestures/.metadata new file mode 100644 index 000000000..a11a679fc --- /dev/null +++ b/doc/examples/gestures/.metadata @@ -0,0 +1,10 @@ +# This file tracks properties of this Flutter project. +# Used by Flutter tool to assess capabilities and perform upgrades etc. +# +# This file should be version controlled and should not be manually edited. + +version: + revision: 841707365a9be08f2219cbafc52c52d6af5355aa + channel: master + +project_type: app diff --git a/doc/examples/gestures/README.md b/doc/examples/gestures/README.md new file mode 100644 index 000000000..58ae0bc8a --- /dev/null +++ b/doc/examples/gestures/README.md @@ -0,0 +1,3 @@ +# gestures + +A flame game showcasing the use of gestures callbacks diff --git a/doc/examples/gestures/lib/main.dart b/doc/examples/gestures/lib/main.dart new file mode 100644 index 000000000..1a87639bf --- /dev/null +++ b/doc/examples/gestures/lib/main.dart @@ -0,0 +1,50 @@ +import 'package:flutter/material.dart'; +import 'package:flame/game.dart'; + +void main() { + final game = MyGame(); + runApp(game.widget); +} + +class MyGame extends Game { + final _whitePaint = Paint()..color = const Color(0xFFFFFFFF); + final _bluePaint = Paint()..color = const Color(0xFF0000FF); + final _greenPaint = Paint()..color = const Color(0xFF00FF00); + + Paint _paint; + + Rect _rect = const Rect.fromLTWH(50, 50, 50, 50); + + MyGame() { + _paint = _whitePaint; + } + + @override + void onTap() { + _paint = _paint == _whitePaint ? _bluePaint : _whitePaint; + } + + @override + bool useDoubleTapDetectors() => true; + + @override + void onDoubleTap() { + _paint = _greenPaint; + } + + @override + bool usePanDetectors() => true; + + @override + void onPanUpdate(DragUpdateDetails details) { + _rect = _rect.translate(details.delta.dx, details.delta.dy); + } + + @override + void update(double dt) {} + + @override + void render(Canvas canvas) { + canvas.drawRect(_rect, _paint); + } +} diff --git a/doc/examples/gestures/pubspec.yaml b/doc/examples/gestures/pubspec.yaml new file mode 100644 index 000000000..5a74dc912 --- /dev/null +++ b/doc/examples/gestures/pubspec.yaml @@ -0,0 +1,16 @@ +name: gestures +description: A flame game showcasing the use of gestures callbacks + +version: 1.0.0+1 + +environment: + sdk: ">=2.1.0 <3.0.0" + +dependencies: + flutter: + sdk: flutter + flame: + path: ../../../ + +flutter: + uses-material-design: false diff --git a/lib/game.dart b/lib/game.dart index 129ee1315..2e6c41df3 100644 --- a/lib/game.dart +++ b/lib/game.dart @@ -19,38 +19,55 @@ import 'position.dart'; /// Subclass this to implement the [update] and [render] methods. /// Flame will deal with calling these methods properly when the game's widget is rendered. abstract class Game { + bool useTapDetectors() => true; void onTap() {} void onTapCancel() {} void onTapDown(TapDownDetails details) {} void onTapUp(TapUpDetails details) {} + + bool useSecondaryTapDetectors() => false; void onSecondaryTapDown(TapDownDetails details) {} void onSecondaryTapUp(TapUpDetails details) {} void onSecondaryTapCancel() {} + + bool useDoubleTapDetectors() => false; void onDoubleTap() {} + + bool useLongPressDetectors() => false; void onLongPress() {} void onLongPressStart(LongPressStartDetails details) {} void onLongPressMoveUpdate(LongPressMoveUpdateDetails details) {} void onLongPressUp() {} void onLongPressEnd(LongPressEndDetails details) {} + + bool useVerticalDragDetectors() => false; void onVerticalDragDown(DragDownDetails details) {} void onVerticalDragStart(DragStartDetails details) {} void onVerticalDragUpdate(DragUpdateDetails details) {} void onVerticalDragEnd(DragEndDetails details) {} void onVerticalDragCancel() {} + + bool useHorizontalDragDetectors() => false; void onHorizontalDragDown(DragDownDetails details) {} void onHorizontalDragStart(DragStartDetails details) {} void onHorizontalDragUpdate(DragUpdateDetails details) {} void onHorizontalDragEnd(DragEndDetails details) {} void onHorizontalDragCancel() {} + + bool useForcePressDetectors() => false; void onForcePressStart(ForcePressDetails details) {} void onForcePressPeak(ForcePressDetails details) {} void onForcePressUpdate(ForcePressDetails details) {} void onForcePressEnd(ForcePressDetails details) {} + + bool usePanDetectors() => false; void onPanDown(DragDownDetails details) {} void onPanStart(DragStartDetails details) {} void onPanUpdate(DragUpdateDetails details) {} void onPanEnd(DragEndDetails details) {} void onPanCancel() {} + + bool useScaleDetectors() => false; void onScaleStart(ScaleStartDetails details) {} void onScaleUpdate(ScaleUpdateDetails details) {} void onScaleEnd(ScaleEndDetails details) {} @@ -96,45 +113,63 @@ class WidgetBuilder { Widget build(Game game) { return GestureDetector( - onTap: () => game.onTap(), - onTapCancel: () => game.onTapCancel(), - onTapDown: (TapDownDetails d) => game.onTapDown(d), - onTapUp: (TapUpDetails d) => game.onTapUp(d), - onSecondaryTapDown: (TapDownDetails d) => game.onSecondaryTapDown(d), - onSecondaryTapUp: (TapUpDetails d) => game.onSecondaryTapUp(d), - onSecondaryTapCancel: () => game.onSecondaryTapCancel(), - onDoubleTap: () => game.onDoubleTap(), - onLongPress: () => game.onLongPress(), - onLongPressStart: (LongPressStartDetails d) => game.onLongPressStart(d), - onLongPressMoveUpdate: (LongPressMoveUpdateDetails d) => + // Taps + onTap: !game.useTapDetectors() ? null : () => game.onTap(), + onTapCancel: !game.useTapDetectors() ? null : () => game.onTapCancel(), + onTapDown: !game.useTapDetectors() ? null : (TapDownDetails d) => game.onTapDown(d), + onTapUp: !game.useTapDetectors() ? null : (TapUpDetails d) => game.onTapUp(d), + + // Secondary taps + onSecondaryTapDown: !game.useSecondaryTapDetectors() ? null : (TapDownDetails d) => game.onSecondaryTapDown(d), + onSecondaryTapUp: !game.useSecondaryTapDetectors() ? null : (TapUpDetails d) => game.onSecondaryTapUp(d), + onSecondaryTapCancel: !game.useSecondaryTapDetectors() ? null : () => game.onSecondaryTapCancel(), + + // Double tap + onDoubleTap: !game.useDoubleTapDetectors() ? null : () => game.onDoubleTap(), + + // Long presses + onLongPress: !game.useLongPressDetectors() ? null : () => game.onLongPress(), + onLongPressStart: !game.useLongPressDetectors() ? null : (LongPressStartDetails d) => game.onLongPressStart(d), + onLongPressMoveUpdate: !game.useLongPressDetectors() ? null : (LongPressMoveUpdateDetails d) => game.onLongPressMoveUpdate(d), - onLongPressUp: () => game.onLongPressUp(), - onLongPressEnd: (LongPressEndDetails d) => game.onLongPressEnd(d), - onVerticalDragDown: (DragDownDetails d) => game.onVerticalDragDown(d), - onVerticalDragStart: (DragStartDetails d) => game.onVerticalDragStart(d), - onVerticalDragUpdate: (DragUpdateDetails d) => + onLongPressUp: !game.useLongPressDetectors() ? null : () => game.onLongPressUp(), + onLongPressEnd: !game.useLongPressDetectors() ? null : (LongPressEndDetails d) => game.onLongPressEnd(d), + + // Vertical drag + onVerticalDragDown: !game.useVerticalDragDetectors() ? null : (DragDownDetails d) => game.onVerticalDragDown(d), + onVerticalDragStart: !game.useVerticalDragDetectors() ? null : (DragStartDetails d) => game.onVerticalDragStart(d), + onVerticalDragUpdate: !game.useVerticalDragDetectors() ? null : (DragUpdateDetails d) => game.onVerticalDragUpdate(d), - onVerticalDragEnd: (DragEndDetails d) => game.onVerticalDragEnd(d), - onVerticalDragCancel: () => game.onVerticalDragCancel(), - onHorizontalDragDown: (DragDownDetails d) => game.onHorizontalDragDown(d), - onHorizontalDragStart: (DragStartDetails d) => + onVerticalDragEnd: !game.useVerticalDragDetectors() ? null : (DragEndDetails d) => game.onVerticalDragEnd(d), + onVerticalDragCancel: !game.useVerticalDragDetectors() ? null : () => game.onVerticalDragCancel(), + + // Horizontal drag + onHorizontalDragDown: !game.useHorizontalDragDetectors() ? null : (DragDownDetails d) => game.onHorizontalDragDown(d), + onHorizontalDragStart: !game.useHorizontalDragDetectors() ? null : (DragStartDetails d) => game.onHorizontalDragStart(d), - onHorizontalDragUpdate: (DragUpdateDetails d) => + onHorizontalDragUpdate: !game.useHorizontalDragDetectors() ? null : (DragUpdateDetails d) => game.onHorizontalDragUpdate(d), - onHorizontalDragEnd: (DragEndDetails d) => game.onHorizontalDragEnd(d), - onHorizontalDragCancel: () => game.onHorizontalDragCancel(), - onForcePressStart: (ForcePressDetails d) => game.onForcePressStart(d), - onForcePressPeak: (ForcePressDetails d) => game.onForcePressPeak(d), - onForcePressUpdate: (ForcePressDetails d) => game.onForcePressUpdate(d), - onForcePressEnd: (ForcePressDetails d) => game.onForcePressEnd(d), - onPanDown: (DragDownDetails d) => game.onPanDown(d), - onPanStart: (DragStartDetails d) => game.onPanStart(d), - onPanUpdate: (DragUpdateDetails d) => game.onPanUpdate(d), - onPanEnd: (DragEndDetails d) => game.onPanEnd(d), - onPanCancel: () => game.onPanCancel(), - onScaleStart: (ScaleStartDetails d) => game.onScaleStart(d), - onScaleUpdate: (ScaleUpdateDetails d) => game.onScaleUpdate(d), - onScaleEnd: (ScaleEndDetails d) => game.onScaleEnd(d), + onHorizontalDragEnd: !game.useHorizontalDragDetectors() ? null : (DragEndDetails d) => game.onHorizontalDragEnd(d), + onHorizontalDragCancel: !game.useHorizontalDragDetectors() ? null : () => game.onHorizontalDragCancel(), + + // Force presses + onForcePressStart: !game.useForcePressDetectors() ? null : (ForcePressDetails d) => game.onForcePressStart(d), + onForcePressPeak: !game.useForcePressDetectors() ? null : (ForcePressDetails d) => game.onForcePressPeak(d), + onForcePressUpdate: !game.useForcePressDetectors() ? null : (ForcePressDetails d) => game.onForcePressUpdate(d), + onForcePressEnd: !game.useForcePressDetectors() ? null : (ForcePressDetails d) => game.onForcePressEnd(d), + + // Pan + onPanDown: !game.usePanDetectors() ? null : (DragDownDetails d) => game.onPanDown(d), + onPanStart: !game.usePanDetectors() ? null : (DragStartDetails d) => game.onPanStart(d), + onPanUpdate: !game.usePanDetectors() ? null : (DragUpdateDetails d) => game.onPanUpdate(d), + onPanEnd: !game.usePanDetectors() ? null : (DragEndDetails d) => game.onPanEnd(d), + onPanCancel: !game.usePanDetectors() ? null : () => game.onPanCancel(), + + // Scales + onScaleStart: !game.useScaleDetectors() ? null : (ScaleStartDetails d) => game.onScaleStart(d), + onScaleUpdate: !game.useScaleDetectors() ? null : (ScaleUpdateDetails d) => game.onScaleUpdate(d), + onScaleEnd: !game.useScaleDetectors() ? null : (ScaleEndDetails d) => game.onScaleEnd(d), + child: Container( color: const Color(0xFF000000), child: Directionality(