33 Commits

Author SHA1 Message Date
accd0cad43 Fix 2803,2802,2800 2024-04-03 21:39:12 +09:00
7e6b5f887a Fix 2796 2024-04-03 20:44:30 +09:00
dd36ab8399 update 2024-03-09 11:59:42 +05:30
b37a33bc2f update versionto 33 2024-03-08 19:17:31 +05:30
e35608651b fix goal reset 2024-03-08 19:14:03 +05:30
c6eb97bbb2 updated for retain rogainin after goal 2024-03-08 18:19:18 +05:30
cb3a843566 update popup conditions 2024-03-08 15:31:49 +05:30
f5922d9034 disabled spinner on matrix 2024-03-07 12:27:30 +05:30
1414d370f4 fixed route 2024-03-06 15:07:14 +05:30
e30c5f255c updated start condition 2024-03-06 14:24:32 +05:30
e6a7d37519 fixed popup buttons added location stream and center button 2024-03-06 11:40:00 +05:30
2f329669e9 fixed position error and added goad condition button 2024-03-05 19:32:42 +05:30
773650be82 disabled gps zoom to current location when popup 2024-03-05 15:43:13 +05:30
cd258744fc updated cp start back to minus one and auto center timer to 10 sec 2024-03-05 12:20:24 +05:30
eaee1ce820 added cp zzero also to start icon 2024-03-04 21:18:22 +05:30
d7ff309c09 disabled auto popup for cp zero 2024-03-03 18:38:22 +05:30
d55ba7cfdb update buttons 2024-03-02 11:11:46 +05:30
992f9f3414 added disabled feature to buttons and reset on start 2024-02-26 20:23:58 +05:30
c3cb6d758c update for network issue 2024-02-19 09:54:06 +05:30
cfa9e055f5 updated to resume in hibernate and set gps accuray to 15m 2024-02-06 15:22:27 +05:30
494b27bf9e added game status 2024-02-04 19:14:41 +05:30
eda5f77e2d fixed cance recipt image 2024-01-18 22:24:51 +05:30
b9e4df069f update goal condition for more that 1000 m away 2024-01-18 19:58:00 +05:30
2fb095bd50 commented print statements 2024-01-18 17:11:36 +05:30
591b6f7aed update waypoint marker positions 2024-01-18 15:21:26 +05:30
8e050267e1 update for always checkin points 2024-01-17 16:08:41 +05:30
c95cb75934 update for checkin radius 2024-01-14 23:01:09 +05:30
0b5ce75d6c update label to black and white 2024-01-08 15:14:44 +05:30
c67914f286 update log for error and disabled log window 2024-01-06 23:02:12 +05:30
9145e0e27d fixed multi popup on camera page 2023-12-18 09:22:18 +05:30
445c53d21b updated map markers 2023-12-12 16:16:17 +05:30
56c07852f9 changed GPS listener 2023-12-07 10:20:44 +05:30
fa0587178f map updated to 6 2023-12-06 11:16:17 +05:30
45 changed files with 2195 additions and 1435 deletions

View File

@ -21,6 +21,6 @@
<key>CFBundleVersion</key> <key>CFBundleVersion</key>
<string>1.0</string> <string>1.0</string>
<key>MinimumOSVersion</key> <key>MinimumOSVersion</key>
<string>11.0</string> <string>12.0</string>
</dict> </dict>
</plist> </plist>

View File

@ -1,5 +1,5 @@
# Uncomment this line to define a global platform for your project # Uncomment this line to define a global platform for your project
# platform :ios, '11.0' platform :ios, '12.0'
# CocoaPods analytics sends network stats synchronously affecting flutter build latency. # CocoaPods analytics sends network stats synchronously affecting flutter build latency.
ENV['COCOAPODS_DISABLE_STATS'] = 'true' ENV['COCOAPODS_DISABLE_STATS'] = 'true'

View File

@ -12,10 +12,10 @@ PODS:
- FMDB (2.7.5): - FMDB (2.7.5):
- FMDB/standard (= 2.7.5) - FMDB/standard (= 2.7.5)
- FMDB/standard (2.7.5) - FMDB/standard (2.7.5)
- gallery_saver (0.0.1):
- Flutter
- geolocator_apple (1.2.0): - geolocator_apple (1.2.0):
- Flutter - Flutter
- image_gallery_saver (2.0.2):
- Flutter
- image_picker_ios (0.0.1): - image_picker_ios (0.0.1):
- Flutter - Flutter
- isar_flutter_libs (1.0.0): - isar_flutter_libs (1.0.0):
@ -23,7 +23,9 @@ PODS:
- path_provider_foundation (0.0.1): - path_provider_foundation (0.0.1):
- Flutter - Flutter
- FlutterMacOS - FlutterMacOS
- permission_handler_apple (9.1.1): - permission_handler_apple (9.3.0):
- Flutter
- pointer_interceptor_ios (0.0.1):
- Flutter - Flutter
- ReachabilitySwift (5.0.0) - ReachabilitySwift (5.0.0)
- shared_preferences_foundation (0.0.1): - shared_preferences_foundation (0.0.1):
@ -41,12 +43,13 @@ DEPENDENCIES:
- Flutter (from `Flutter`) - Flutter (from `Flutter`)
- flutter_compass (from `.symlinks/plugins/flutter_compass/ios`) - flutter_compass (from `.symlinks/plugins/flutter_compass/ios`)
- flutter_keyboard_visibility (from `.symlinks/plugins/flutter_keyboard_visibility/ios`) - flutter_keyboard_visibility (from `.symlinks/plugins/flutter_keyboard_visibility/ios`)
- gallery_saver (from `.symlinks/plugins/gallery_saver/ios`)
- geolocator_apple (from `.symlinks/plugins/geolocator_apple/ios`) - geolocator_apple (from `.symlinks/plugins/geolocator_apple/ios`)
- image_gallery_saver (from `.symlinks/plugins/image_gallery_saver/ios`)
- image_picker_ios (from `.symlinks/plugins/image_picker_ios/ios`) - image_picker_ios (from `.symlinks/plugins/image_picker_ios/ios`)
- isar_flutter_libs (from `.symlinks/plugins/isar_flutter_libs/ios`) - isar_flutter_libs (from `.symlinks/plugins/isar_flutter_libs/ios`)
- path_provider_foundation (from `.symlinks/plugins/path_provider_foundation/darwin`) - path_provider_foundation (from `.symlinks/plugins/path_provider_foundation/darwin`)
- permission_handler_apple (from `.symlinks/plugins/permission_handler_apple/ios`) - permission_handler_apple (from `.symlinks/plugins/permission_handler_apple/ios`)
- pointer_interceptor_ios (from `.symlinks/plugins/pointer_interceptor_ios/ios`)
- shared_preferences_foundation (from `.symlinks/plugins/shared_preferences_foundation/darwin`) - shared_preferences_foundation (from `.symlinks/plugins/shared_preferences_foundation/darwin`)
- sqflite (from `.symlinks/plugins/sqflite/ios`) - sqflite (from `.symlinks/plugins/sqflite/ios`)
- url_launcher_ios (from `.symlinks/plugins/url_launcher_ios/ios`) - url_launcher_ios (from `.symlinks/plugins/url_launcher_ios/ios`)
@ -67,10 +70,10 @@ EXTERNAL SOURCES:
:path: ".symlinks/plugins/flutter_compass/ios" :path: ".symlinks/plugins/flutter_compass/ios"
flutter_keyboard_visibility: flutter_keyboard_visibility:
:path: ".symlinks/plugins/flutter_keyboard_visibility/ios" :path: ".symlinks/plugins/flutter_keyboard_visibility/ios"
gallery_saver:
:path: ".symlinks/plugins/gallery_saver/ios"
geolocator_apple: geolocator_apple:
:path: ".symlinks/plugins/geolocator_apple/ios" :path: ".symlinks/plugins/geolocator_apple/ios"
image_gallery_saver:
:path: ".symlinks/plugins/image_gallery_saver/ios"
image_picker_ios: image_picker_ios:
:path: ".symlinks/plugins/image_picker_ios/ios" :path: ".symlinks/plugins/image_picker_ios/ios"
isar_flutter_libs: isar_flutter_libs:
@ -79,6 +82,8 @@ EXTERNAL SOURCES:
:path: ".symlinks/plugins/path_provider_foundation/darwin" :path: ".symlinks/plugins/path_provider_foundation/darwin"
permission_handler_apple: permission_handler_apple:
:path: ".symlinks/plugins/permission_handler_apple/ios" :path: ".symlinks/plugins/permission_handler_apple/ios"
pointer_interceptor_ios:
:path: ".symlinks/plugins/pointer_interceptor_ios/ios"
shared_preferences_foundation: shared_preferences_foundation:
:path: ".symlinks/plugins/shared_preferences_foundation/darwin" :path: ".symlinks/plugins/shared_preferences_foundation/darwin"
sqflite: sqflite:
@ -87,23 +92,24 @@ EXTERNAL SOURCES:
:path: ".symlinks/plugins/url_launcher_ios/ios" :path: ".symlinks/plugins/url_launcher_ios/ios"
SPEC CHECKSUMS: SPEC CHECKSUMS:
camera_avfoundation: 3125e8cd1a4387f6f31c6c63abb8a55892a9eeeb camera_avfoundation: 759172d1a77ae7be0de08fc104cfb79738b8a59e
connectivity_plus: 07c49e96d7fc92bc9920617b83238c4d178b446a connectivity_plus: bf0076dd84a130856aa636df1c71ccaff908fa1d
Flutter: f04841e97a9d0b0a8025694d0796dd46242b2854 Flutter: e0871f40cf51350855a761d2e70bf5af5b9b5de7
flutter_compass: cbbd285cea1584c7ac9c4e0c3e1f17cbea55e855 flutter_compass: cbbd285cea1584c7ac9c4e0c3e1f17cbea55e855
flutter_keyboard_visibility: 0339d06371254c3eb25eeb90ba8d17dca8f9c069 flutter_keyboard_visibility: 0339d06371254c3eb25eeb90ba8d17dca8f9c069
FMDB: 2ce00b547f966261cd18927a3ddb07cb6f3db82a FMDB: 2ce00b547f966261cd18927a3ddb07cb6f3db82a
gallery_saver: 9fc173c9f4fcc48af53b2a9ebea1b643255be542 geolocator_apple: 9157311f654584b9bb72686c55fc02a97b73f461
geolocator_apple: cc556e6844d508c95df1e87e3ea6fa4e58c50401 image_gallery_saver: cb43cc43141711190510e92c460eb1655cd343cb
image_picker_ios: 4a8aadfbb6dc30ad5141a2ce3832af9214a705b5 image_picker_ios: 99dfe1854b4fa34d0364e74a78448a0151025425
isar_flutter_libs: b69f437aeab9c521821c3f376198c4371fa21073 isar_flutter_libs: b69f437aeab9c521821c3f376198c4371fa21073
path_provider_foundation: 29f094ae23ebbca9d3d0cec13889cd9060c0e943 path_provider_foundation: 3784922295ac71e43754bd15e0653ccfd36a147c
permission_handler_apple: e76247795d700c14ea09e3a2d8855d41ee80a2e6 permission_handler_apple: 9878588469a2b0d0fc1e048d9f43605f92e6cec2
pointer_interceptor_ios: 9280618c0b2eeb80081a343924aa8ad756c21375
ReachabilitySwift: 985039c6f7b23a1da463388634119492ff86c825 ReachabilitySwift: 985039c6f7b23a1da463388634119492ff86c825
shared_preferences_foundation: 5b919d13b803cadd15ed2dc053125c68730e5126 shared_preferences_foundation: b4c3b4cddf1c21f02770737f147a3f5da9d39695
sqflite: 31f7eba61e3074736dff8807a9b41581e4f7f15a sqflite: 50a33e1d72bd59ee092a519a35d107502757ebed
url_launcher_ios: 08a3dfac5fb39e8759aeb0abbd5d9480f30fc8b4 url_launcher_ios: bbd758c6e7f9fd7b5b1d4cde34d2b95fcce5e812
PODFILE CHECKSUM: a1c2f8dde3796ecc1697a15e7c75eb5205d8a740 PODFILE CHECKSUM: 7a34d5e980f9e05ecf4e24c79da64ca020615638
COCOAPODS: 1.12.1 COCOAPODS: 1.15.2

View File

@ -139,6 +139,7 @@
9705A1C41CF9048500538489 /* Embed Frameworks */, 9705A1C41CF9048500538489 /* Embed Frameworks */,
3B06AD1E1E4923F5004D2608 /* Thin Binary */, 3B06AD1E1E4923F5004D2608 /* Thin Binary */,
CD1CB185AC38B6B245F9A672 /* [CP] Embed Pods Frameworks */, CD1CB185AC38B6B245F9A672 /* [CP] Embed Pods Frameworks */,
4D62FB08D65E9D3D4D84B418 /* [CP] Copy Pods Resources */,
); );
buildRules = ( buildRules = (
); );
@ -213,6 +214,23 @@
shellPath = /bin/sh; shellPath = /bin/sh;
shellScript = "/bin/sh \"$FLUTTER_ROOT/packages/flutter_tools/bin/xcode_backend.sh\" embed_and_thin"; shellScript = "/bin/sh \"$FLUTTER_ROOT/packages/flutter_tools/bin/xcode_backend.sh\" embed_and_thin";
}; };
4D62FB08D65E9D3D4D84B418 /* [CP] Copy Pods Resources */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputFileListPaths = (
"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources-${CONFIGURATION}-input-files.xcfilelist",
);
name = "[CP] Copy Pods Resources";
outputFileListPaths = (
"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources-${CONFIGURATION}-output-files.xcfilelist",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "\"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources.sh\"\n";
showEnvVarsInLog = 0;
};
9740EEB61CF901F6004384FC /* Run Script */ = { 9740EEB61CF901F6004384FC /* Run Script */ = {
isa = PBXShellScriptBuildPhase; isa = PBXShellScriptBuildPhase;
alwaysOutOfDate = 1; alwaysOutOfDate = 1;
@ -342,7 +360,7 @@
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES; GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES; GCC_WARN_UNUSED_VARIABLE = YES;
IPHONEOS_DEPLOYMENT_TARGET = 11.0; IPHONEOS_DEPLOYMENT_TARGET = 12.0;
MTL_ENABLE_DEBUG_INFO = NO; MTL_ENABLE_DEBUG_INFO = NO;
ONLY_ACTIVE_ARCH = YES; ONLY_ACTIVE_ARCH = YES;
SDKROOT = iphoneos; SDKROOT = iphoneos;
@ -358,17 +376,25 @@
buildSettings = { buildSettings = {
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
CLANG_ENABLE_MODULES = YES; CLANG_ENABLE_MODULES = YES;
CURRENT_PROJECT_VERSION = "$(FLUTTER_BUILD_NUMBER)"; CODE_SIGN_IDENTITY = "Apple Development";
DEVELOPMENT_TEAM = ECMVJVB7LV; CODE_SIGN_STYLE = Automatic;
CURRENT_PROJECT_VERSION = 453;
DEVELOPMENT_TEAM = UMNEWT25JR;
ENABLE_BITCODE = NO; ENABLE_BITCODE = NO;
FLUTTER_BUILD_NAME = 4.5.0;
FLUTTER_BUILD_NUMBER = 453;
INFOPLIST_FILE = Runner/Info.plist; INFOPLIST_FILE = Runner/Info.plist;
INFOPLIST_KEY_CFBundleDisplayName = "岐阜ナビ";
INFOPLIST_KEY_LSApplicationCategoryType = "public.app-category.healthcare-fitness";
IPHONEOS_DEPLOYMENT_TARGET = 12.0; IPHONEOS_DEPLOYMENT_TARGET = 12.0;
LD_RUNPATH_SEARCH_PATHS = ( LD_RUNPATH_SEARCH_PATHS = (
"$(inherited)", "$(inherited)",
"@executable_path/Frameworks", "@executable_path/Frameworks",
); );
MARKETING_VERSION = 4.5.0;
PRODUCT_BUNDLE_IDENTIFIER = com.dvox.gifunavi; PRODUCT_BUNDLE_IDENTIFIER = com.dvox.gifunavi;
PRODUCT_NAME = "$(TARGET_NAME)"; PRODUCT_NAME = "$(TARGET_NAME)";
PROVISIONING_PROFILE_SPECIFIER = "";
SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h";
SWIFT_VERSION = 5.0; SWIFT_VERSION = 5.0;
VERSIONING_SYSTEM = "apple-generic"; VERSIONING_SYSTEM = "apple-generic";
@ -422,7 +448,7 @@
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES; GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES; GCC_WARN_UNUSED_VARIABLE = YES;
IPHONEOS_DEPLOYMENT_TARGET = 11.0; IPHONEOS_DEPLOYMENT_TARGET = 12.0;
MTL_ENABLE_DEBUG_INFO = YES; MTL_ENABLE_DEBUG_INFO = YES;
ONLY_ACTIVE_ARCH = YES; ONLY_ACTIVE_ARCH = YES;
SDKROOT = iphoneos; SDKROOT = iphoneos;
@ -471,7 +497,7 @@
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES; GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES; GCC_WARN_UNUSED_VARIABLE = YES;
IPHONEOS_DEPLOYMENT_TARGET = 11.0; IPHONEOS_DEPLOYMENT_TARGET = 12.0;
MTL_ENABLE_DEBUG_INFO = NO; MTL_ENABLE_DEBUG_INFO = NO;
ONLY_ACTIVE_ARCH = YES; ONLY_ACTIVE_ARCH = YES;
SDKROOT = iphoneos; SDKROOT = iphoneos;
@ -489,17 +515,25 @@
buildSettings = { buildSettings = {
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
CLANG_ENABLE_MODULES = YES; CLANG_ENABLE_MODULES = YES;
CURRENT_PROJECT_VERSION = "$(FLUTTER_BUILD_NUMBER)"; CODE_SIGN_IDENTITY = "Apple Development";
DEVELOPMENT_TEAM = ECMVJVB7LV; CODE_SIGN_STYLE = Automatic;
CURRENT_PROJECT_VERSION = 453;
DEVELOPMENT_TEAM = UMNEWT25JR;
ENABLE_BITCODE = NO; ENABLE_BITCODE = NO;
FLUTTER_BUILD_NAME = 4.5.0;
FLUTTER_BUILD_NUMBER = 453;
INFOPLIST_FILE = Runner/Info.plist; INFOPLIST_FILE = Runner/Info.plist;
INFOPLIST_KEY_CFBundleDisplayName = "岐阜ナビ";
INFOPLIST_KEY_LSApplicationCategoryType = "public.app-category.healthcare-fitness";
IPHONEOS_DEPLOYMENT_TARGET = 12.0; IPHONEOS_DEPLOYMENT_TARGET = 12.0;
LD_RUNPATH_SEARCH_PATHS = ( LD_RUNPATH_SEARCH_PATHS = (
"$(inherited)", "$(inherited)",
"@executable_path/Frameworks", "@executable_path/Frameworks",
); );
MARKETING_VERSION = 4.5.0;
PRODUCT_BUNDLE_IDENTIFIER = com.dvox.gifunavi; PRODUCT_BUNDLE_IDENTIFIER = com.dvox.gifunavi;
PRODUCT_NAME = "$(TARGET_NAME)"; PRODUCT_NAME = "$(TARGET_NAME)";
PROVISIONING_PROFILE_SPECIFIER = "";
SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h";
SWIFT_OPTIMIZATION_LEVEL = "-Onone"; SWIFT_OPTIMIZATION_LEVEL = "-Onone";
SWIFT_VERSION = 5.0; SWIFT_VERSION = 5.0;
@ -513,17 +547,25 @@
buildSettings = { buildSettings = {
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
CLANG_ENABLE_MODULES = YES; CLANG_ENABLE_MODULES = YES;
CURRENT_PROJECT_VERSION = "$(FLUTTER_BUILD_NUMBER)"; CODE_SIGN_IDENTITY = "Apple Development";
DEVELOPMENT_TEAM = ECMVJVB7LV; CODE_SIGN_STYLE = Automatic;
CURRENT_PROJECT_VERSION = 453;
DEVELOPMENT_TEAM = UMNEWT25JR;
ENABLE_BITCODE = NO; ENABLE_BITCODE = NO;
FLUTTER_BUILD_NAME = 4.5.0;
FLUTTER_BUILD_NUMBER = 453;
INFOPLIST_FILE = Runner/Info.plist; INFOPLIST_FILE = Runner/Info.plist;
INFOPLIST_KEY_CFBundleDisplayName = "岐阜ナビ";
INFOPLIST_KEY_LSApplicationCategoryType = "public.app-category.healthcare-fitness";
IPHONEOS_DEPLOYMENT_TARGET = 12.0; IPHONEOS_DEPLOYMENT_TARGET = 12.0;
LD_RUNPATH_SEARCH_PATHS = ( LD_RUNPATH_SEARCH_PATHS = (
"$(inherited)", "$(inherited)",
"@executable_path/Frameworks", "@executable_path/Frameworks",
); );
MARKETING_VERSION = 4.5.0;
PRODUCT_BUNDLE_IDENTIFIER = com.dvox.gifunavi; PRODUCT_BUNDLE_IDENTIFIER = com.dvox.gifunavi;
PRODUCT_NAME = "$(TARGET_NAME)"; PRODUCT_NAME = "$(TARGET_NAME)";
PROVISIONING_PROFILE_SPECIFIER = "";
SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h";
SWIFT_VERSION = 5.0; SWIFT_VERSION = 5.0;
VERSIONING_SYSTEM = "apple-generic"; VERSIONING_SYSTEM = "apple-generic";

View File

@ -65,5 +65,7 @@
<true/> <true/>
<key>UIApplicationSupportsIndirectInputEvents</key> <key>UIApplicationSupportsIndirectInputEvents</key>
<true/> <true/>
<key>FLTEnableImpeller</key>
<false/>
</dict> </dict>
</plist> </plist>

View File

@ -4,6 +4,7 @@ import 'package:get/get.dart';
import 'package:rogapp/pages/destination/destination_controller.dart'; import 'package:rogapp/pages/destination/destination_controller.dart';
import 'package:rogapp/pages/index/index_binding.dart'; import 'package:rogapp/pages/index/index_binding.dart';
import 'package:rogapp/routes/app_pages.dart'; import 'package:rogapp/routes/app_pages.dart';
import 'package:rogapp/utils/location_controller.dart';
import 'package:rogapp/utils/string_values.dart'; import 'package:rogapp/utils/string_values.dart';
import 'package:shared_preferences/shared_preferences.dart'; import 'package:shared_preferences/shared_preferences.dart';
// import 'package:is_lock_screen/is_lock_screen.dart'; // import 'package:is_lock_screen/is_lock_screen.dart';
@ -15,6 +16,7 @@ void saveGameState() async {
pref.setBool("is_in_rog", destinationController.isInRog.value); pref.setBool("is_in_rog", destinationController.isInRog.value);
pref.setBool( pref.setBool(
"rogaining_counted", destinationController.rogainingCounted.value); "rogaining_counted", destinationController.rogainingCounted.value);
pref.setBool("ready_for_goal", DestinationController.ready_for_goal);
} }
void restoreGame() async { void restoreGame() async {
@ -25,6 +27,8 @@ void restoreGame() async {
destinationController.isInRog.value = pref.getBool("is_in_rog") ?? false; destinationController.isInRog.value = pref.getBool("is_in_rog") ?? false;
destinationController.rogainingCounted.value = destinationController.rogainingCounted.value =
pref.getBool("rogaining_counted") ?? false; pref.getBool("rogaining_counted") ?? false;
DestinationController.ready_for_goal =
pref.getBool("ready_for_goal") ?? false;
//print( //print(
// "--restored -- destinationController.isInRog.value ${pref.getBool("is_in_rog")} -- ${pref.getBool("rogaining_counted")}"); // "--restored -- destinationController.isInRog.value ${pref.getBool("is_in_rog")} -- ${pref.getBool("rogaining_counted")}");
} }
@ -84,25 +88,32 @@ class _MyAppState extends State<MyApp> with WidgetsBindingObserver {
@override @override
void didChangeAppLifecycleState(AppLifecycleState state) { void didChangeAppLifecycleState(AppLifecycleState state) {
LocationController locationController = Get.find<LocationController>();
DestinationController destinationController = DestinationController destinationController =
Get.find<DestinationController>(); Get.find<DestinationController>();
switch (state) { switch (state) {
case AppLifecycleState.resumed: case AppLifecycleState.resumed:
locationController.resumePositionStream();
//print("RESUMED"); //print("RESUMED");
restoreGame(); restoreGame();
break; break;
case AppLifecycleState.inactive: case AppLifecycleState.inactive:
locationController.resumePositionStream();
//print("INACTIVE"); //print("INACTIVE");
break; break;
case AppLifecycleState.paused: case AppLifecycleState.paused:
locationController.resumePositionStream();
//print("PAUSED"); //print("PAUSED");
saveGameState(); saveGameState();
break; break;
case AppLifecycleState.detached: case AppLifecycleState.detached:
locationController.resumePositionStream();
//print("DETACHED"); //print("DETACHED");
saveGameState(); saveGameState();
break; break;
case AppLifecycleState.hidden: case AppLifecycleState.hidden:
locationController.resumePositionStream();
//print("DETACHED"); //print("DETACHED");
saveGameState(); saveGameState();
break; break;

View File

@ -1,6 +1,6 @@
import 'dart:async'; import 'dart:async';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_map/plugin_api.dart'; import 'package:flutter_map/flutter_map.dart';
import 'package:flutter_map_location_marker/flutter_map_location_marker.dart'; import 'package:flutter_map_location_marker/flutter_map_location_marker.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart'; import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:latlong2/latlong.dart'; import 'package:latlong2/latlong.dart';

View File

@ -136,7 +136,9 @@ class CameraPage extends StatelessWidget {
} }
if (destinationController.isAtGoal.value && if (destinationController.isAtGoal.value &&
destinationController.isInRog.value) { destinationController.isInRog.value &&
destination.cp == -1) {
//goal
return Row( return Row(
mainAxisAlignment: MainAxisAlignment.spaceAround, mainAxisAlignment: MainAxisAlignment.spaceAround,
children: [ children: [
@ -189,7 +191,8 @@ class CameraPage extends StatelessWidget {
Get.back(); Get.back();
destinationController.skipGps = false; destinationController.skipGps = false;
Get.snackbar("目標が保存されました", "目標が正常に追加されました"); Get.snackbar("目標が保存されました", "目標が正常に追加されました");
destinationController.resetRogaining(); destinationController.resetRogaining(
isgoal: true);
} else { } else {
//print("---- status ${value['status']} ---- "); //print("---- status ${value['status']} ---- ");
Get.snackbar("目標が追加されていません", "please_try_again"); Get.snackbar("目標が追加されていません", "please_try_again");
@ -210,6 +213,7 @@ class CameraPage extends StatelessWidget {
); );
} else if (destinationController.isInRog.value && } else if (destinationController.isInRog.value &&
dbDest?.checkedin != null && dbDest?.checkedin != null &&
destination.cp != -1 &&
dbDest?.checkedin == true) { dbDest?.checkedin == true) {
//make buypoint image //make buypoint image
return Row( return Row(
@ -396,45 +400,6 @@ class StartRogaining extends StatelessWidget {
} }
} }
// class NotAtGoal extends StatelessWidget {
// NotAtGoal({Key? key}) : super(key: key);
// DestinationController destinationController =
// Get.find<DestinationController>();
// @override
// Widget build(BuildContext context) {
// return Scaffold(
// appBar: AppBar(
// title: Text(
// "Not reached the goal yet".tr,
// ),
// ),
// body: Container(
// child: Center(
// child: Column(
// mainAxisAlignment: MainAxisAlignment.center,
// children: [
// Text("You have not reached the goal yet.".tr,
// style: const TextStyle(fontSize: 24)),
// const SizedBox(
// height: 40.0,
// ),
// ElevatedButton(
// onPressed: () {
// Get.back();
// destinationController.skip_gps = false;
// },
// child: const Text("Back"),
// ),
// ],
// ),
// ),
// ),
// );
// }
// }
class BuyPointCamera extends StatelessWidget { class BuyPointCamera extends StatelessWidget {
BuyPointCamera({Key? key, required this.destination}) : super(key: key); BuyPointCamera({Key? key, required this.destination}) : super(key: key);
@ -445,6 +410,8 @@ class BuyPointCamera extends StatelessWidget {
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
//print("in camera purchase 1 ${destinationController.isInRog.value}");
return Scaffold( return Scaffold(
appBar: AppBar( appBar: AppBar(
automaticallyImplyLeading: false, automaticallyImplyLeading: false,
@ -482,6 +449,8 @@ class BuyPointCamera extends StatelessWidget {
children: [ children: [
ElevatedButton( ElevatedButton(
onPressed: () { onPressed: () {
// print(
// "in camera purchase 2 ${destinationController.isInRog.value}");
destinationController.openCamera( destinationController.openCamera(
context, destination); context, destination);
}, },
@ -495,7 +464,8 @@ class BuyPointCamera extends StatelessWidget {
onPressed: () async { onPressed: () async {
await destinationController await destinationController
.cancelBuyPoint(destination); .cancelBuyPoint(destination);
Get.back(); Navigator.of(Get.context!).pop();
//Get.back();
destinationController.rogainingCounted.value = true; destinationController.rogainingCounted.value = true;
destinationController.skipGps = false; destinationController.skipGps = false;
destinationController.isPhotoShoot.value = false; destinationController.isPhotoShoot.value = false;
@ -519,10 +489,14 @@ class BuyPointCamera extends StatelessWidget {
style: ElevatedButton.styleFrom( style: ElevatedButton.styleFrom(
backgroundColor: Colors.red), backgroundColor: Colors.red),
onPressed: () async { onPressed: () async {
// print(
// "in camera purchase 3 ${destinationController.isInRog.value}");
await destinationController.makeBuyPoint( await destinationController.makeBuyPoint(
destination, destination,
destinationController.photos[0].path); destinationController.photos[0].path);
Get.back(); Get.back();
// print(
// "in camera purchase 4 ${destinationController.isInRog.value}");
destinationController.rogainingCounted.value = destinationController.rogainingCounted.value =
true; true;
destinationController.skipGps = false; destinationController.skipGps = false;

View File

@ -1,8 +1,10 @@
import 'dart:io'; import 'dart:io';
import 'dart:typed_data';
import 'package:camera_camera/camera_camera.dart'; import 'package:camera_camera/camera_camera.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_map/flutter_map.dart'; import 'package:flutter_map/flutter_map.dart';
import 'package:geojson/geojson.dart'; import 'package:flutter_map_location_marker/flutter_map_location_marker.dart';
import 'package:geojson_vi/geojson_vi.dart';
import 'package:geolocator/geolocator.dart'; import 'package:geolocator/geolocator.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:intl/intl.dart'; import 'package:intl/intl.dart';
@ -13,6 +15,7 @@ import 'package:rogapp/model/gps_data.dart';
import 'package:rogapp/pages/camera/camera_page.dart'; import 'package:rogapp/pages/camera/camera_page.dart';
import 'package:rogapp/pages/index/index_controller.dart'; import 'package:rogapp/pages/index/index_controller.dart';
import 'package:rogapp/routes/app_pages.dart'; import 'package:rogapp/routes/app_pages.dart';
import 'package:rogapp/services/DatabaseService.dart';
import 'package:rogapp/services/destination_service.dart'; import 'package:rogapp/services/destination_service.dart';
import 'package:rogapp/services/external_service.dart'; import 'package:rogapp/services/external_service.dart';
import 'package:rogapp/services/location_service.dart'; import 'package:rogapp/services/location_service.dart';
@ -20,13 +23,15 @@ import 'package:rogapp/services/maxtrix_service.dart';
import 'package:rogapp/services/perfecture_service.dart'; import 'package:rogapp/services/perfecture_service.dart';
import 'package:rogapp/utils/database_gps.dart'; import 'package:rogapp/utils/database_gps.dart';
import 'package:rogapp/utils/database_helper.dart'; import 'package:rogapp/utils/database_helper.dart';
import 'package:rogapp/utils/location_controller.dart';
import 'package:rogapp/widgets/bottom_sheet_new.dart'; import 'package:rogapp/widgets/bottom_sheet_new.dart';
import 'dart:async'; import 'dart:async';
import 'package:modal_bottom_sheet/modal_bottom_sheet.dart'; import 'package:modal_bottom_sheet/modal_bottom_sheet.dart';
import 'package:rogapp/widgets/debug_widget.dart'; import 'package:rogapp/widgets/debug_widget.dart';
import 'package:shared_preferences/shared_preferences.dart'; import 'package:shared_preferences/shared_preferences.dart';
import 'package:gallery_saver/gallery_saver.dart';
import 'package:image_gallery_saver/image_gallery_saver.dart';
class DestinationController extends GetxController { class DestinationController extends GetxController {
late LocationSettings locationSettings; late LocationSettings locationSettings;
@ -39,8 +44,11 @@ class DestinationController extends GetxController {
double currentLon = 0.0; double currentLon = 0.0;
DateTime lastGPSCollectedTime = DateTime.now(); DateTime lastGPSCollectedTime = DateTime.now();
bool shouldShowBottomSheet = true;
static bool gps_push_started = false; static bool gps_push_started = false;
static bool game_started = false; static bool game_started = false;
static bool ready_for_goal = false;
bool skip_10s = false; bool skip_10s = false;
@ -70,6 +78,8 @@ class DestinationController extends GetxController {
final photos = <File>[].obs; final photos = <File>[].obs;
final IndexController indexController = Get.find<IndexController>(); final IndexController indexController = Get.find<IndexController>();
final LocationController locationController = Get.put(LocationController());
final DatabaseService dbService = DatabaseService();
int _start = 0; int _start = 0;
int chekcs = 0; int chekcs = 0;
@ -79,10 +89,9 @@ class DestinationController extends GetxController {
return DateFormat('yyyy-MM-dd HH:mm:ss').format(datetime); return DateFormat('yyyy-MM-dd HH:mm:ss').format(datetime);
} }
Destination festuretoDestination(GeoJsonFeature fs) { Destination festuretoDestination(GeoJSONFeature fs) {
GeoJsonMultiPoint mp = fs.geometry as GeoJsonMultiPoint; GeoJSONMultiPoint mp = fs.geometry as GeoJSONMultiPoint;
LatLng pt = LatLng(mp.geoSerie!.geoPoints[0].latitude, LatLng pt = LatLng(mp.coordinates[0][1], mp.coordinates[0][0]);
mp.geoSerie!.geoPoints[0].longitude);
//print("----- ${indexController.currentFeature[0].properties} -----"); //print("----- ${indexController.currentFeature[0].properties} -----");
@ -112,7 +121,7 @@ class DestinationController extends GetxController {
tags: fs.properties!["tags"]); tags: fs.properties!["tags"]);
} }
Future<void> startTimerLocation(GeoJsonFeature fs, double distance) async { Future<void> startTimerLocation(GeoJSONFeature fs, double distance) async {
//print("---- in startTimer ----"); //print("---- in startTimer ----");
// print("---- is in rog is $is_in_rog ----"); // print("---- is in rog is $is_in_rog ----");
double checkinRadious = fs.properties!['checkin_radius'] ?? double.infinity; double checkinRadious = fs.properties!['checkin_radius'] ?? double.infinity;
@ -156,7 +165,7 @@ class DestinationController extends GetxController {
//make current destination //make current destination
// print("---- checkin_radious $checkinRadious ----"); // print("---- checkin_radious $checkinRadious ----");
// print("---- distance $distance ----"); // print("---- distance $distance ----");
if (checkinRadious >= distance) { if (checkinRadious >= distance || checkinRadious == -1) {
//currentSelectedDestinations.add(d); //currentSelectedDestinations.add(d);
indexController.currentDestinationFeature.clear(); indexController.currentDestinationFeature.clear();
indexController.currentDestinationFeature.add(d); indexController.currentDestinationFeature.add(d);
@ -170,15 +179,22 @@ class DestinationController extends GetxController {
if (isPhotoShoot.value == true) { if (isPhotoShoot.value == true) {
photos.clear(); photos.clear();
if (shouldShowBottomSheet) {
shouldShowBottomSheet = false;
if (d.cp == -1) return;
await showModalBottomSheet( await showModalBottomSheet(
constraints: BoxConstraints.loose(Size(Get.width, Get.height * 0.75)), constraints:
BoxConstraints.loose(Size(Get.width, Get.height * 0.75)),
context: Get.context!, context: Get.context!,
isScrollControlled: true, isScrollControlled: true,
builder: ((context) => CameraPage(destination: d))).whenComplete(() { builder: ((context) => CameraPage(destination: d)))
.whenComplete(() {
shouldShowBottomSheet = true;
skipGps = false; skipGps = false;
chekcs = 0; chekcs = 0;
isInCheckin.value = false; isInCheckin.value = false;
}); });
}
return; return;
} }
@ -192,6 +208,9 @@ class DestinationController extends GetxController {
chekcs = 1; chekcs = 1;
isInCheckin.value = true; isInCheckin.value = true;
isAtStart.value = true; isAtStart.value = true;
if (shouldShowBottomSheet) {
shouldShowBottomSheet = false;
if (d.cp == -1) return;
await showModalBottomSheet( await showModalBottomSheet(
constraints: constraints:
BoxConstraints.loose(Size(Get.width, Get.height * 0.85)), BoxConstraints.loose(Size(Get.width, Get.height * 0.85)),
@ -200,16 +219,23 @@ class DestinationController extends GetxController {
builder: ((context) => BottomSheetNew( builder: ((context) => BottomSheetNew(
destination: d, destination: d,
))).whenComplete(() { ))).whenComplete(() {
shouldShowBottomSheet = true;
skipGps = false; skipGps = false;
chekcs = 0; chekcs = 0;
isAtStart.value = false; isAtStart.value = false;
isInCheckin.value = false; isInCheckin.value = false;
}); });
}
return; return;
} else if (isInRog.value == true && indexController.rogMode.value == 1) { } else if (isInRog.value == true &&
indexController.rogMode.value == 1 &&
d.cp != -1) {
// print("----- in location popup checkin cp - ${d.cp}----"); // print("----- in location popup checkin cp - ${d.cp}----");
chekcs = 2; chekcs = 2;
isInCheckin.value = true; isInCheckin.value = true;
if (shouldShowBottomSheet) {
shouldShowBottomSheet = false;
if (d.cp == -1) return;
await showModalBottomSheet( await showModalBottomSheet(
constraints: constraints:
BoxConstraints.loose(Size(Get.width, Get.height * 0.75)), BoxConstraints.loose(Size(Get.width, Get.height * 0.75)),
@ -218,17 +244,19 @@ class DestinationController extends GetxController {
builder: ((context) => BottomSheetNew( builder: ((context) => BottomSheetNew(
destination: d, destination: d,
))).whenComplete(() { ))).whenComplete(() {
shouldShowBottomSheet = true;
skipGps = false; skipGps = false;
chekcs = 0; chekcs = 0;
isInCheckin.value = false; isInCheckin.value = false;
}); });
}
return; return;
} }
} }
// print("---- location checkin radious ${d.checkin_radious} ----"); // print("---- location checkin radious ${d.checkin_radious} ----");
// print("---- already checked in $locationAlreadyCheckedIn ----"); // print("---- already checked in $locationAlreadyCheckedIn ----");
if (checkinRadious >= distance && if ((checkinRadious >= distance || checkinRadious == -1) &&
locationAlreadyCheckedIn == false && locationAlreadyCheckedIn == false &&
isInRog.value == true) { isInRog.value == true) {
if (autoCheckin) { if (autoCheckin) {
@ -253,6 +281,9 @@ class DestinationController extends GetxController {
isInCheckin.value = true; isInCheckin.value = true;
photos.clear(); photos.clear();
// print("--- calling checkin ---"); // print("--- calling checkin ---");
if (shouldShowBottomSheet) {
shouldShowBottomSheet = false;
if (d.cp == -1) return;
await showModalBottomSheet( await showModalBottomSheet(
constraints: constraints:
BoxConstraints.loose(Size(Get.width, Get.height * 0.75)), BoxConstraints.loose(Size(Get.width, Get.height * 0.75)),
@ -261,15 +292,20 @@ class DestinationController extends GetxController {
builder: ((context) => CameraPage( builder: ((context) => CameraPage(
destination: d, destination: d,
))).whenComplete(() { ))).whenComplete(() {
shouldShowBottomSheet = true;
skipGps = false; skipGps = false;
rogainingCounted.value = true; rogainingCounted.value = true;
chekcs = 0; chekcs = 0;
isInCheckin.value = false; isInCheckin.value = false;
}); });
}
return; return;
} else if (isInRog.value == true && d.cp != -1) { } else if (isInRog.value == true && d.cp != -1) {
chekcs = 4; chekcs = 4;
isInCheckin.value = true; isInCheckin.value = true;
if (shouldShowBottomSheet) {
shouldShowBottomSheet = false;
if (d.cp == -1) return;
await showMaterialModalBottomSheet( await showMaterialModalBottomSheet(
expand: true, expand: true,
context: Get.context!, context: Get.context!,
@ -277,14 +313,16 @@ class DestinationController extends GetxController {
builder: (context) => BottomSheetNew( builder: (context) => BottomSheetNew(
destination: d, destination: d,
)).whenComplete(() { )).whenComplete(() {
shouldShowBottomSheet = true;
skipGps = false; skipGps = false;
chekcs = 0; chekcs = 0;
isInCheckin.value = false; isInCheckin.value = false;
}); });
}
return; return;
} }
} }
} else if (checkinRadious >= distance && } else if ((checkinRadious >= distance || checkinRadious == -1) &&
locationAlreadyCheckedIn == true && locationAlreadyCheckedIn == true &&
buyPointImageAdded == false && buyPointImageAdded == false &&
ds.isNotEmpty && ds.isNotEmpty &&
@ -295,8 +333,12 @@ class DestinationController extends GetxController {
isInCheckin.value = true; isInCheckin.value = true;
photos.clear(); photos.clear();
//print("--- open buy point $buyPointImageAdded ${d.buypoint_image} ----"); //print("--- open buy point $buyPointImageAdded ${d.buypoint_image} ----");
if (shouldShowBottomSheet) {
shouldShowBottomSheet = false;
if (d.cp == -1) return;
await showModalBottomSheet( await showModalBottomSheet(
constraints: BoxConstraints.loose(Size(Get.width, Get.height * 0.75)), constraints:
BoxConstraints.loose(Size(Get.width, Get.height * 0.75)),
context: Get.context!, context: Get.context!,
isScrollControlled: true, isScrollControlled: true,
builder: ((context) => CameraPage( builder: ((context) => CameraPage(
@ -304,11 +346,13 @@ class DestinationController extends GetxController {
destination: d, destination: d,
dbDest: ds.first, dbDest: ds.first,
))).whenComplete(() { ))).whenComplete(() {
shouldShowBottomSheet = true;
skipGps = false; skipGps = false;
rogainingCounted.value = true; rogainingCounted.value = true;
chekcs = 0; chekcs = 0;
isInCheckin.value = false; isInCheckin.value = false;
}); });
}
return; return;
} }
// print("---- cp --- ${d.cp} -----"); // print("---- cp --- ${d.cp} -----");
@ -328,6 +372,9 @@ class DestinationController extends GetxController {
chekcs = 5; chekcs = 5;
isAtGoal.value = true; isAtGoal.value = true;
photos.clear(); photos.clear();
if (shouldShowBottomSheet) {
shouldShowBottomSheet = false;
if (d.cp == -1) return;
await showModalBottomSheet( await showModalBottomSheet(
constraints: constraints:
BoxConstraints.loose(Size(Get.width, Get.height * 0.75)), BoxConstraints.loose(Size(Get.width, Get.height * 0.75)),
@ -336,10 +383,12 @@ class DestinationController extends GetxController {
builder: ((context) => CameraPage( builder: ((context) => CameraPage(
destination: d, destination: d,
))).whenComplete(() { ))).whenComplete(() {
shouldShowBottomSheet = true;
skipGps = false; skipGps = false;
chekcs = 0; chekcs = 0;
isAtGoal.value = false; isAtGoal.value = false;
}); });
}
return; return;
} else if (isInRog.value == false && } else if (isInRog.value == false &&
indexController.rogMode.value == 1 && indexController.rogMode.value == 1 &&
@ -348,6 +397,9 @@ class DestinationController extends GetxController {
//print("---- in start -----"); //print("---- in start -----");
chekcs = 6; chekcs = 6;
isAtStart.value = true; isAtStart.value = true;
if (shouldShowBottomSheet) {
shouldShowBottomSheet = false;
if (d.cp == -1) return;
await showModalBottomSheet( await showModalBottomSheet(
constraints: constraints:
BoxConstraints.loose(Size(Get.width, Get.height * 0.75)), BoxConstraints.loose(Size(Get.width, Get.height * 0.75)),
@ -356,11 +408,13 @@ class DestinationController extends GetxController {
builder: ((context) => BottomSheetNew( builder: ((context) => BottomSheetNew(
destination: d, destination: d,
))).whenComplete(() { ))).whenComplete(() {
shouldShowBottomSheet = true;
//print("----- finished start -------"); //print("----- finished start -------");
skipGps = false; skipGps = false;
chekcs = 0; chekcs = 0;
isAtStart.value = false; isAtStart.value = false;
}); });
}
return; return;
} }
} }
@ -371,7 +425,7 @@ class DestinationController extends GetxController {
return; return;
} }
Future<void> resetRogaining() async { Future<void> resetRogaining({bool isgoal = false}) async {
//print("----- resetting --------"); //print("----- resetting --------");
isInCheckin.value = false; isInCheckin.value = false;
@ -380,17 +434,25 @@ class DestinationController extends GetxController {
isAtGoal.value = false; isAtGoal.value = false;
isGpsSelected.value = true; isGpsSelected.value = true;
skipGps = false; skipGps = false;
ready_for_goal = false;
_start = 0; _start = 0;
chekcs = 0; chekcs = 0;
rogainingCounted.value = false; rogainingCounted.value = false;
DatabaseHelper db = DatabaseHelper.instance; DatabaseHelper db = DatabaseHelper.instance;
if (isgoal == false) {
await db.deleteAllDestinations();
await db.deleteAllRogaining();
}
int? latgoal = await db.latestGoal(); int? latgoal = await db.latestGoal();
if (latgoal != null) { if (latgoal != null) {
lastGoalAt = DateTime.fromMicrosecondsSinceEpoch(latgoal); lastGoalAt = DateTime.fromMicrosecondsSinceEpoch(latgoal);
//print("===== last goal : $last_goal_at ====="); //print("===== last goal : $last_goal_at =====");
} }
dbService.updateDatabase();
} }
void deleteAllDestinations() { void deleteAllDestinations() {
@ -499,12 +561,21 @@ class DestinationController extends GetxController {
} }
}); });
} else { } else {
Get.snackbar("始まっていない", "ロゲイニングを始める必要があります"); Get.snackbar(
"始まっていません",
"ロゲ開始ボタンをタップして、ロゲイニングを始める必要があります",
icon: const Icon(Icons.assistant_photo_outlined, size: 40.0, color: Colors.blue),
snackPosition: SnackPosition.TOP,
duration: const Duration(seconds: 3),
backgroundColor: Colors.yellow,
);
} }
} }
} }
Future<void> addGPStoDB(double la, double ln, {isCheckin = 0}) async { Future<void> addGPStoDB(double la, double ln, {isCheckin = 0}) async {
//print("in addGPStoDB ${indexController.currentUser}");
try {
GpsDatabaseHelper db = GpsDatabaseHelper.instance; GpsDatabaseHelper db = GpsDatabaseHelper.instance;
final team_name = indexController.currentUser[0]["user"]['team_name']; final team_name = indexController.currentUser[0]["user"]['team_name'];
final event_code = indexController.currentUser[0]["user"]["event_code"]; final event_code = indexController.currentUser[0]["user"]["event_code"];
@ -517,85 +588,36 @@ class DestinationController extends GetxController {
is_checkin: isCheckin, is_checkin: isCheckin,
created_at: DateTime.now().millisecondsSinceEpoch); created_at: DateTime.now().millisecondsSinceEpoch);
var res = await db.insertGps(gps_data); var res = await db.insertGps(gps_data);
//print("==gps res == ${res}"); } catch (err) {
print("errr ready gps ${err}");
return;
}
} }
Future<void> checkForCheckin() async { Future<void> checkForCheckin() async {
//print("--- Start of checkForCheckin function ---"); //print("--- Start of checkForCheckin function ---");
dbService.updateDatabase();
await Future.delayed(const Duration(milliseconds: 3000));
game_started = true; game_started = true;
try { try {
//print("--- 000 ---- $skip_gps----"); indexController.locations[0].features.forEach((fs) async {
await Future.delayed(const Duration(milliseconds: 3000)); GeoJSONMultiPoint mp = fs!.geometry as GeoJSONMultiPoint;
Position position = await Geolocator.getCurrentPosition( LatLng pt = LatLng(mp.coordinates[0][1], mp.coordinates[0][0]);
desiredAccuracy: LocationAccuracy.bestForNavigation);
currentLat = position.latitude;
currentLon = position.longitude;
final la = position.latitude;
final ln = position.longitude;
LogManager().addLog(
"GPS : $currentLat, $currentLon - ${DateTime.now().hour}:${DateTime.now().minute}:${DateTime.now().second}:${DateTime.now().microsecond}");
//print("--- gps is ${la}, ${ln}");
//add gps to database
//check distance to previous point
var distance = const Distance();
double distanceToDest = distance.as(
LengthUnit.Meter,
LatLng(position.latitude, position.longitude),
LatLng(currentLat, currentLon));
Duration difference =
lastGPSCollectedTime.difference(DateTime.now()).abs();
if (difference.inSeconds >= 10 || distanceToDest >= 10) {
print(
"^^^^^^^^ GPS data collected ${DateFormat('kk:mm:ss \n EEE d MMM').format(DateTime.now())}, ^^^ ${position.latitude}, ${position.longitude}");
await addGPStoDB(la, ln);
lastGPSCollectedTime = DateTime.now();
}
// GpsDatabaseHelper db = GpsDatabaseHelper.instance;
// final team_name = indexController.currentUser[0]["user"]['team_name'];
// final event_code = indexController.currentUser[0]["user"]["event_code"];
// print("--- curr gps is ${la}, ${ln}");
// GpsData gps_data = GpsData(
// id: 0,
// team_name: team_name,
// event_code: event_code,
// lat: la,
// lon: ln,
// created_at: DateTime.now().microsecondsSinceEpoch);
// await db.insertGps(gps_data);
for (GeoJsonFeature fs in indexController.locations[0].collection) {
GeoJsonMultiPoint mp = fs.geometry as GeoJsonMultiPoint;
LatLng pt = LatLng(mp.geoSerie!.geoPoints[0].latitude,
mp.geoSerie!.geoPoints[0].longitude);
double latFs = pt.latitude; double latFs = pt.latitude;
double lonFs = pt.longitude; double lonFs = pt.longitude;
var distanceFs = const Distance(); var distanceFs = const Distance();
//print("--- points : ${pt.latitude}, ${pt.longitude} ----"); double distFs = distanceFs.as(LengthUnit.Meter, LatLng(latFs, lonFs),
//print("--- points : ${pt.latitude}, ${pt.longitude} ----"); LatLng(currentLat, currentLon));
double distFs = distanceFs.as(
LengthUnit.Meter, LatLng(latFs, lonFs), LatLng(la, ln));
Destination des = festuretoDestination(fs); Destination des = festuretoDestination(fs);
//print(
// "--- position is ---- ${position.longitude}, --- ${position.longitude}----");
//print("--- distFs ---- $distFs, --- ${des.checkin_radious}----");
if (distFs <= des.checkin_radious! && skipGps == false) { if (distFs <= des.checkin_radious! && skipGps == false) {
//print("--- 789 ---- $skip_gps----");
//near a location
//print("---- before call startTimerLocation ----");
await startTimerLocation(fs, distFs); await startTimerLocation(fs, distFs);
break; // Note: You cannot break out of forEach. If you need to stop processing, you might have to reconsider using forEach.
}
} }
});
if (gps_push_started == false) { if (gps_push_started == false) {
pushGPStoServer(); pushGPStoServer();
} }
@ -644,11 +666,21 @@ class DestinationController extends GetxController {
populateDestinations(); populateDestinations();
} }
_saveImageFromPath(String imagePath) async {
// Read the image file from the given path
File imageFile = File(imagePath);
Uint8List imageBytes = await imageFile.readAsBytes();
// Save the image to the gallery
final result = await ImageGallerySaver.saveImage(imageBytes);
//print("--- save result --- ${result}");
}
Future<void> makeBuyPoint(Destination destination, String imageurl) async { Future<void> makeBuyPoint(Destination destination, String imageurl) async {
DatabaseHelper db = DatabaseHelper.instance; DatabaseHelper db = DatabaseHelper.instance;
await db.updateBuyPoint(destination, imageurl); await db.updateBuyPoint(destination, imageurl);
populateDestinations(); populateDestinations();
await GallerySaver.saveImage(imageurl); await _saveImageFromPath(imageurl);
if (indexController.currentUser.isNotEmpty) { if (indexController.currentUser.isNotEmpty) {
double cpNum = destination.cp!; double cpNum = destination.cp!;
@ -690,7 +722,7 @@ class DestinationController extends GetxController {
// print("~~~~ inserted into db ~~~~"); // print("~~~~ inserted into db ~~~~");
} }
await GallerySaver.saveImage(imageurl); await _saveImageFromPath(imageurl);
populateDestinations(); populateDestinations();
@ -719,9 +751,11 @@ class DestinationController extends GetxController {
// print("------Ext service check point $value ------"); // print("------Ext service check point $value ------");
}); });
} }
dbService.updateDatabase();
} }
Future<void> removeCheckin(int cp) { Future<void> removeCheckin(int cp) {
dbService.updateDatabase();
return ExternalService().removeCheckin(cp); return ExternalService().removeCheckin(cp);
} }
@ -734,20 +768,84 @@ class DestinationController extends GetxController {
@override @override
void onInit() async { void onInit() async {
startGame();
super.onInit(); super.onInit();
locationController.locationMarkerPositionStream.listen(
(locationMarkerPosition) {
if (locationMarkerPosition != null) {
handleLocationUpdate(locationMarkerPosition);
}
}, onError: (err) {
print("Error: $err");
});
startGame();
}
@override
void onClose() {
locationController.stopPositionStream();
}
void handleLocationUpdate(LocationMarkerPosition? position) async {
try {
if (position != null) {
if (distanceToStart() >= 150) {
ready_for_goal = true;
}
var distance = const Distance();
double distanceToDest = distance.as(
LengthUnit.Meter,
LatLng(position.latitude, position.longitude),
LatLng(currentLat, currentLon));
Duration difference =
lastGPSCollectedTime.difference(DateTime.now()).abs();
if (difference.inSeconds >= 10 || distanceToDest >= 10) {
// print(
// "^^^^^^^^ GPS data collected ${DateFormat('kk:mm:ss \n EEE d MMM').format(DateTime.now())}, ^^^ ${position.latitude}, ${position.longitude}");
LogManager().addLog(
"GPS : $currentLat, $currentLon - ${DateTime.now().hour}:${DateTime.now().minute}:${DateTime.now().second}:${DateTime.now().microsecond}");
if (isInRog.value) {
await addGPStoDB(position.latitude, position.longitude);
lastGPSCollectedTime = DateTime.now();
}
}
}
} finally {
if (position != null &&
(position.latitude != 0 && position.longitude != 0)) {
currentLat = position.latitude;
currentLon = position.longitude;
}
}
} }
double distanceToStart() { double distanceToStart() {
if (indexController.locations.isEmpty) {
return 1000000000;
}
//print("=== gfs len == ${indexController.locations[0].collection.length}"); //print("=== gfs len == ${indexController.locations[0].collection.length}");
GeoJsonFeature gfs = indexController.locations[0].collection double distanceToDest = double.infinity;
.firstWhere((element) => festuretoDestination(element).cp == -1); if (indexController.locations[0].features.isEmpty) {
return distanceToDest;
}
GeoJSONFeature? gfs = indexController.locations[0].features.firstWhere(
(element) => festuretoDestination(element!).cp == -1,
orElse: () => null, // Provide a null value if no element is found
);
//print("gfs : ${gfs}");
if (gfs == null) {
return distanceToDest;
}
Destination des = festuretoDestination(gfs); Destination des = festuretoDestination(gfs);
//print("=== gfs == ${des.toMap()}"); //print("=== gfs == ${des.toMap()}");
double distanceToDest = double.infinity;
var distance = const Distance(); var distance = const Distance();
distanceToDest = distance.as(LengthUnit.Meter, distanceToDest = distance.as(LengthUnit.Meter,
LatLng(currentLat, currentLon), LatLng(des.lat!, des.lon!)); LatLng(currentLat, currentLon), LatLng(des.lat!, des.lon!));
@ -756,13 +854,23 @@ class DestinationController extends GetxController {
} }
int getForcedChckinDistance(Destination dest) { int getForcedChckinDistance(Destination dest) {
if (dest.checkin_radious == -1) {
return 10000000000000000;
}
int _retValue = 100; int _retValue = 100;
if (dest.cp == -1) { if (dest.cp == -1) {
return 500; return 500;
} }
Destination? ds; Destination? ds;
GeoJsonFeature gfs = indexController.locations[0].collection GeoJSONFeature? gfs = indexController.locations[0].features.firstWhere(
.firstWhere((element) => festuretoDestination(element).cp == -1); (element) => festuretoDestination(element!).cp == -1,
orElse: () => null, // Provide a null value if no element is found
);
if (gfs == null) {
return _retValue;
}
ds = festuretoDestination(gfs); ds = festuretoDestination(gfs);
var distance = const Distance(); var distance = const Distance();
@ -824,10 +932,22 @@ class DestinationController extends GetxController {
indexController.currentBound.clear(); indexController.currentBound.clear();
indexController.currentBound.add(bnds); indexController.currentBound.add(bnds);
indexController.loadLocationsBound(); indexController.loadLocationsBound();
centerMapToCurrentLocation();
} }
}); });
} }
void centerMapToCurrentLocation() {
assert(() {
print("center is ${currentLon}, ${currentLon}");
return true;
}());
// Akira
if (currentLat != 0 || currentLon != 0) {
indexController.mapController.move(LatLng(currentLat, currentLon), 17.0);
}
}
void connectionChanged(String val) { void connectionChanged(String val) {
//print('----- %%%%%%%%%%%%%%%%%%%%% ----- $val'); //print('----- %%%%%%%%%%%%%%%%%%%%% ----- $val');
Map<String, dynamic> res = {}; Map<String, dynamic> res = {};
@ -903,6 +1023,7 @@ class DestinationController extends GetxController {
db.deleteDestination(d.location_id!).then((value) { db.deleteDestination(d.location_id!).then((value) {
populateDestinations(); populateDestinations();
}); });
dbService.updateDatabase();
} }
void deleteDBDestinations() { void deleteDBDestinations() {
@ -910,6 +1031,7 @@ class DestinationController extends GetxController {
db.deleteAllDestinations().then((value) { db.deleteAllDestinations().then((value) {
populateDestinations(); populateDestinations();
}); });
dbService.updateDatabase();
} }
// ---------- database ------------------/// // ---------- database ------------------///
@ -932,6 +1054,7 @@ class DestinationController extends GetxController {
}); });
} }
}); });
dbService.updateDatabase();
} }
void toggleSelection(Destination dest) async { void toggleSelection(Destination dest) async {
@ -965,7 +1088,7 @@ class DestinationController extends GetxController {
} }
void destinationMatrixFromCurrentPoint(List<Destination> points) { void destinationMatrixFromCurrentPoint(List<Destination> points) {
buildShowDialog(Get.context!); //buildShowDialog(Get.context!);
MatrixService.getDestinations(points).then((mat) { MatrixService.getDestinations(points).then((mat) {
//print(" matrix is ------- $mat"); //print(" matrix is ------- $mat");
matrix = mat; matrix = mat;
@ -984,7 +1107,7 @@ class DestinationController extends GetxController {
skipGps = false; skipGps = false;
return; return;
} finally { } finally {
Get.back(); //Get.back();
} }
}); });
} }

View File

@ -1,7 +1,7 @@
import 'dart:async'; import 'dart:async';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_map/plugin_api.dart'; import 'package:flutter_map/flutter_map.dart';
import 'package:flutter_map_location_marker/flutter_map_location_marker.dart'; import 'package:flutter_map_location_marker/flutter_map_location_marker.dart';
import 'package:flutter_map_marker_popup/flutter_map_marker_popup.dart'; import 'package:flutter_map_marker_popup/flutter_map_marker_popup.dart';
import 'package:flutter_polyline_points/flutter_polyline_points.dart'; import 'package:flutter_polyline_points/flutter_polyline_points.dart';
@ -42,9 +42,8 @@ class DestinationMapPage extends StatelessWidget {
//print("^^^^ $d ^^^^"); //print("^^^^ $d ^^^^");
Marker m = Marker( Marker m = Marker(
point: LatLng(d.lat!, d.lon!), point: LatLng(d.lat!, d.lon!),
anchorPos: AnchorPos.align(AnchorAlign.center), alignment: Alignment.center,
builder: (cts) { child: InkWell(
return InkWell(
onTap: () { onTap: () {
//print("-- Destination is --- ${d.name} ------"); //print("-- Destination is --- ${d.name} ------");
if (indexController.currentDestinationFeature.isNotEmpty) { if (indexController.currentDestinationFeature.isNotEmpty) {
@ -56,8 +55,8 @@ class DestinationMapPage extends StatelessWidget {
showModalBottomSheet( showModalBottomSheet(
context: Get.context!, context: Get.context!,
isScrollControlled: true, isScrollControlled: true,
constraints: BoxConstraints.loose( constraints:
Size(Get.width, Get.height * 0.85)), BoxConstraints.loose(Size(Get.width, Get.height * 0.85)),
builder: ((context) => BottomSheetNew( builder: ((context) => BottomSheetNew(
destination: d, destination: d,
))).whenComplete(() { ))).whenComplete(() {
@ -76,8 +75,7 @@ class DestinationMapPage extends StatelessWidget {
shape: BoxShape.circle, shape: BoxShape.circle,
border: Border.all( border: Border.all(
color: Colors.white, color: Colors.white,
width: width: d.checkin_radious != null ? d.checkin_radious! : 1,
d.checkin_radious != null ? d.checkin_radious! : 1,
), ),
), ),
child: Center( child: Center(
@ -98,8 +96,7 @@ class DestinationMapPage extends StatelessWidget {
)), )),
], ],
), ),
); ));
});
pts.add(m); pts.add(m);
} }

View File

@ -115,9 +115,10 @@ class _GpsPageState extends State<GpsPage> {
]), ]),
zoom: 1, zoom: 1,
interactiveFlags: InteractiveFlag.pinchZoom | InteractiveFlag.drag, interactiveFlags: InteractiveFlag.pinchZoom | InteractiveFlag.drag,
onPositionChanged: (MapPosition pos, bool hasGesture) {
onPositionChanged: (MapPosition pos, isvalue) { if (hasGesture) {
indexController.currentBound = [pos.bounds!]; indexController.currentBound = [pos.bounds!];
}
}, },
onTap: (tapPos, cord) {}, // Hide popup when the map is tapped. onTap: (tapPos, cord) {}, // Hide popup when the map is tapped.
), ),
@ -126,21 +127,23 @@ class _GpsPageState extends State<GpsPage> {
MarkerLayer( MarkerLayer(
markers: gpsData.map((i) { markers: gpsData.map((i) {
return Marker( return Marker(
anchorPos: AnchorPos.exactly(Anchor(108.0, 18.0)), width: 30.0, // Fixed width
height: 32.0, height: 30.0, // Fixed height
width: 120.0,
point: LatLng(i.lat, i.lon), point: LatLng(i.lat, i.lon),
builder: (ctx) { child: getMarkerShape(i),
return getMarkerShape(i); alignment: Alignment.center);
// return Container(
// width: 40,
// height: 40,
// color: Colors.orange,
// );
},
);
}).toList(), }).toList(),
) ),
// MarkerLayer(
// markers: gpsData.map((i) {
// return Marker(
// alignment: Alignment.center,
// height: 32.0,
// width: 120.0,
// point: LatLng(i.lat, i.lon),
// child: getMarkerShape(i));
// }).toList(),
// )
], ],
), ),
)), )),

View File

@ -1,11 +1,13 @@
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:rogapp/pages/destination/destination_controller.dart'; import 'package:rogapp/pages/destination/destination_controller.dart';
import 'package:rogapp/pages/index/index_controller.dart'; import 'package:rogapp/pages/index/index_controller.dart';
import 'package:rogapp/utils/location_controller.dart';
class IndexBinding extends Bindings { class IndexBinding extends Bindings {
@override @override
void dependencies() { void dependencies() {
Get.put<IndexController>(IndexController()); Get.put<IndexController>(IndexController());
Get.put<LocationController>(LocationController());
Get.put<DestinationController>(DestinationController()); Get.put<DestinationController>(DestinationController());
} }
} }

View File

@ -4,9 +4,8 @@ import 'package:connectivity_plus/connectivity_plus.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter/services.dart'; import 'package:flutter/services.dart';
import 'package:flutter_map/flutter_map.dart'; import 'package:flutter_map/flutter_map.dart';
import 'package:flutter_map/plugin_api.dart';
import 'package:flutter_polyline_points/flutter_polyline_points.dart'; import 'package:flutter_polyline_points/flutter_polyline_points.dart';
import 'package:geojson/geojson.dart'; import 'package:geojson_vi/geojson_vi.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:latlong2/latlong.dart'; import 'package:latlong2/latlong.dart';
import 'package:rogapp/model/destination.dart'; import 'package:rogapp/model/destination.dart';
@ -18,8 +17,8 @@ import 'package:rogapp/utils/database_helper.dart';
import 'package:shared_preferences/shared_preferences.dart'; import 'package:shared_preferences/shared_preferences.dart';
class IndexController extends GetxController { class IndexController extends GetxController {
List<GeoJsonFeatureCollection> locations = <GeoJsonFeatureCollection>[].obs; List<GeoJSONFeatureCollection> locations = <GeoJSONFeatureCollection>[].obs;
List<GeoJsonFeature> currentFeature = <GeoJsonFeature>[].obs; List<GeoJSONFeature> currentFeature = <GeoJSONFeature>[].obs;
List<Destination> currentDestinationFeature = <Destination>[].obs; List<Destination> currentDestinationFeature = <Destination>[].obs;
List<dynamic> perfectures = <dynamic>[].obs; List<dynamic> perfectures = <dynamic>[].obs;
List<LatLngBounds> currentBound = <LatLngBounds>[].obs; List<LatLngBounds> currentBound = <LatLngBounds>[].obs;
@ -173,11 +172,11 @@ class IndexController extends GetxController {
} else { } else {
isLoading.value = false; isLoading.value = false;
Get.snackbar( Get.snackbar(
"Failed", "ログイン失敗",
"User login failed, please try again.", "ログインIDかパスワードを確認して下さい。",
icon: const Icon(Icons.error, size: 40.0, color: Colors.blue), icon: const Icon(Icons.error, size: 40.0, color: Colors.blue),
snackPosition: SnackPosition.TOP, snackPosition: SnackPosition.TOP,
duration: const Duration(milliseconds: 800), duration: const Duration(seconds: 3),
backgroundColor: Colors.yellow, backgroundColor: Colors.yellow,
//icon:Image(image:AssetImage("assets/images/dora.png")) //icon:Image(image:AssetImage("assets/images/dora.png"))
); );
@ -283,6 +282,7 @@ class IndexController extends GetxController {
}); });
} }
/*
void loadLocationsBound() { void loadLocationsBound() {
if (isCustomAreaSelected.value == true) { if (isCustomAreaSelected.value == true) {
return; return;
@ -311,7 +311,7 @@ class IndexController extends GetxController {
if (value == null) { if (value == null) {
return; return;
} }
if (value.collection.isEmpty) { if (value.features.isEmpty) {
if (showPopup == false) { if (showPopup == false) {
return; return;
} }
@ -321,34 +321,104 @@ class IndexController extends GetxController {
icon: const Icon(Icons.assistant_photo_outlined, icon: const Icon(Icons.assistant_photo_outlined,
size: 40.0, color: Colors.blue), size: 40.0, color: Colors.blue),
snackPosition: SnackPosition.TOP, snackPosition: SnackPosition.TOP,
duration: const Duration(milliseconds: 800), duration: const Duration(seconds: 2),
backgroundColor: Colors.yellow, backgroundColor: Colors.yellow,
//icon:Image(image:AssetImage("assets/images/dora.png")) //icon:Image(image:AssetImage("assets/images/dora.png"))
); );
showPopup = false; showPopup = false;
//Get.showSnackbar(GetSnackBar(message: "Too many points, please zoom in",)); //Get.showSnackbar(GetSnackBar(message: "Too many points, please zoom in",));
} }
if (value.collection.isNotEmpty) { if (value.features.isNotEmpty) {
////print("---- added---"); ////print("---- added---");
locations.add(value); locations.add(value);
} }
}); });
} }
*/
// 2024-04-03 Akira .. Update the code . See ticket 2800.
//
void loadLocationsBound() {
if (isCustomAreaSelected.value == true) {
return;
}
locations.clear();
String cat = currentCat.isNotEmpty ? currentCat[0] : "";
if (currentCat.isNotEmpty && currentCat[0] == "-all-") {
cat = "";
}
LatLngBounds bounds = mapController.bounds!;
currentBound.clear();
currentBound.add(bounds);
isLoading.value = true; // ローディング状態をtrueに設定
LocationService.loadLocationsBound(
bounds.southWest.latitude,
bounds.southWest.longitude,
bounds.northWest.latitude,
bounds.northWest.longitude,
bounds.northEast.latitude,
bounds.northEast.longitude,
bounds.southEast.latitude,
bounds.southEast.longitude,
cat
).then((value) {
isLoading.value = false; // ローディング状態をfalseに設定
if (value == null) {
// APIからのレスポンスがnullの場合は処理を中断
return;
}
if (value.features.isEmpty) {
if (showPopup == false) {
return;
}
Get.snackbar(
"Too many Points",
"please zoom in",
icon: const Icon(Icons.assistant_photo_outlined, size: 40.0, color: Colors.blue),
snackPosition: SnackPosition.TOP,
duration: const Duration(seconds: 3),
backgroundColor: Colors.yellow,
);
showPopup = false;
}
if (value.features.isNotEmpty) {
locations.add(value);
}
}).catchError((error) {
isLoading.value = false; // ローディング状態をfalseに設定
// エラーハンドリング: APIリクエストが失敗した場合
Get.snackbar(
"Error",
"Failed to load locations. Please check your internet connection and try again.",
icon: const Icon(Icons.error, size: 40.0, color: Colors.red),
snackPosition: SnackPosition.TOP,
duration: const Duration(milliseconds: 800),
backgroundColor: Colors.yellow,
);
});
}
void setBound(LatLngBounds bounds) { void setBound(LatLngBounds bounds) {
currentBound.clear(); currentBound.clear();
currentBound.add(bounds); currentBound.add(bounds);
} }
GeoJsonFeature? getFeatureForLatLong(double lat, double long) { GeoJSONFeature? getFeatureForLatLong(double lat, double long) {
if (locations.isNotEmpty) { if (locations.isNotEmpty) {
for (GeoJsonFeature i in locations[0].collection) { GeoJSONFeature? foundFeature;
GeoJsonMultiPoint p = i.geometry as GeoJsonMultiPoint;
if (p.geoSerie!.geoPoints[0].latitude == lat && locations[0].features.forEach((i) {
p.geoSerie!.geoPoints[0].longitude == long) { GeoJSONMultiPoint p = i!.geometry as GeoJSONMultiPoint;
return i; if (p.coordinates[0][1] == lat && p.coordinates[0][0] == long) {
} foundFeature = i;
} }
});
return foundFeature;
} }
return null; return null;
} }

View File

@ -1,11 +1,14 @@
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:rogapp/model/destination.dart';
import 'package:rogapp/model/gps_data.dart'; import 'package:rogapp/model/gps_data.dart';
import 'package:rogapp/pages/destination/destination_controller.dart'; import 'package:rogapp/pages/destination/destination_controller.dart';
import 'package:rogapp/pages/drawer/drawer_page.dart'; import 'package:rogapp/pages/drawer/drawer_page.dart';
import 'package:rogapp/pages/index/index_controller.dart'; import 'package:rogapp/pages/index/index_controller.dart';
import 'package:rogapp/routes/app_pages.dart'; import 'package:rogapp/routes/app_pages.dart';
import 'package:rogapp/services/DatabaseService.dart';
import 'package:rogapp/utils/database_gps.dart'; import 'package:rogapp/utils/database_gps.dart';
import 'package:rogapp/utils/database_helper.dart';
import 'package:rogapp/widgets/list_widget.dart'; import 'package:rogapp/widgets/list_widget.dart';
import 'package:rogapp/widgets/map_widget.dart'; import 'package:rogapp/widgets/map_widget.dart';
@ -25,6 +28,13 @@ class IndexPage extends GetView<IndexController> {
appBar: AppBar( appBar: AppBar(
title: Text("add_location".tr), title: Text("add_location".tr),
actions: [ actions: [
// IconButton(
// onPressed: () {
// DatabaseService ds = DatabaseService();
// ds.updateDatabase();
// },
// icon: const Icon(Icons.ten_k_sharp)),
IconButton( IconButton(
onPressed: () async { onPressed: () async {
// GpsDatabaseHelper db = GpsDatabaseHelper.instance; // GpsDatabaseHelper db = GpsDatabaseHelper.instance;

View File

@ -6,11 +6,10 @@ class LoadingPage extends StatelessWidget {
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
return Container( return Container(
alignment: Alignment.topCenter, alignment: Alignment.center,
margin: const EdgeInsets.only(top: 20), margin: const EdgeInsets.only(top: 20),
child: const CircularProgressIndicator( child: const CircularProgressIndicator(
value: 0.8, value: 0.8,
) ));
);
} }
} }

View File

@ -16,6 +16,12 @@ class LoginPage extends StatelessWidget {
return Scaffold( return Scaffold(
resizeToAvoidBottomInset: false, resizeToAvoidBottomInset: false,
backgroundColor: Colors.white, backgroundColor: Colors.white,
appBar: AppBar(
elevation: 0,
backgroundColor: Colors.white,
automaticallyImplyLeading: false,
),
/* 2024-04-03 Updated by Akira . See https://wiki.sumasen.net/issues/2796?issue_count=1&issue_position=1
appBar: AppBar( appBar: AppBar(
elevation: 0, elevation: 0,
backgroundColor: Colors.white, backgroundColor: Colors.white,
@ -29,6 +35,7 @@ class LoginPage extends StatelessWidget {
color: Colors.black, color: Colors.black,
)), )),
), ),
*/
body: indexController.currentUser.isEmpty body: indexController.currentUser.isEmpty
? SizedBox( ? SizedBox(
width: double.infinity, width: double.infinity,
@ -88,7 +95,7 @@ class LoginPage extends StatelessWidget {
MaterialButton( MaterialButton(
minWidth: double.infinity, minWidth: double.infinity,
height: 40, height: 40,
onPressed: () { onPressed: () async {
if (emailController.text.isEmpty || if (emailController.text.isEmpty ||
passwordController passwordController
.text.isEmpty) { .text.isEmpty) {
@ -104,7 +111,7 @@ class LoginPage extends StatelessWidget {
snackPosition: snackPosition:
SnackPosition.TOP, SnackPosition.TOP,
duration: const Duration( duration: const Duration(
milliseconds: 800), seconds: 3),
backgroundColor: Colors.yellow, backgroundColor: Colors.yellow,
//icon:Image(image:AssetImage("assets/images/dora.png")) //icon:Image(image:AssetImage("assets/images/dora.png"))
); );
@ -116,6 +123,30 @@ class LoginPage extends StatelessWidget {
emailController.text, emailController.text,
passwordController.text, passwordController.text,
context); context);
/*
try {
bool isLoggedIn = await indexController.login(emailController.text, passwordController.text,context);
if (isLoggedIn) {
Get.offAllNamed(AppPages.INDEX);
} else {
Get.snackbar(
"Login Failed",
"Invalid email or password",
icon: const Icon(Icons.error, color: Colors.red),
snackPosition: SnackPosition.BOTTOM,
);
}
} catch (e) {
Get.snackbar(
"Error",
"An error occurred during login",
icon: const Icon(Icons.error, color: Colors.red),
snackPosition: SnackPosition.BOTTOM,
);
} finally {
indexController.isLoading.value = false;
}
*/ // ここまで
}, },
color: Colors.indigoAccent[400], color: Colors.indigoAccent[400],
shape: RoundedRectangleBorder( shape: RoundedRectangleBorder(
@ -128,6 +159,16 @@ class LoginPage extends StatelessWidget {
fontSize: 16, fontSize: 16,
color: Colors.white70), color: Colors.white70),
), ),
/*
child: Obx(
() => indexController.isLoading.value
? const CircularProgressIndicator(color: Colors.white)
: const Text(
"ログイン",
style: TextStyle(fontWeight: FontWeight.w600, fontSize: 16, color: Colors.white70),
),
),
*/ // ここまで
), ),
const SizedBox( const SizedBox(
height: 5.0, height: 5.0,
@ -209,7 +250,25 @@ class LoginPage extends StatelessWidget {
), ),
), ),
], ],
) ),
const Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Flexible(
child: Padding(
padding: EdgeInsets.all(8.0),
child: Text(
"※第8回と第9回は、岐阜県からの「清流の国ぎふ」SDGs推進ネットワーク連携促進補助金を受けています",
style: TextStyle(
fontSize:
12, // Consider adjusting the font size if the text is too small.
// Removed overflow: TextOverflow.ellipsis to allow text wrapping.
),
),
),
),
],
),
], ],
), ),
], ],

View File

@ -1,23 +1,21 @@
import 'package:geojson/geojson.dart'; import 'package:geojson_vi/geojson_vi.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:rogapp/pages/index/index_controller.dart'; import 'package:rogapp/pages/index/index_controller.dart';
class SearchBarController extends GetxController { class SearchBarController extends GetxController {
List<GeoJSONFeature> searchResults = <GeoJSONFeature>[].obs;
List<GeoJsonFeature> searchResults = <GeoJsonFeature>[].obs;
@override @override
void onInit() { void onInit() {
IndexController indexController = Get.find<IndexController>(); IndexController indexController = Get.find<IndexController>();
if (indexController.locations.isNotEmpty) { if (indexController.locations.isNotEmpty) {
for(int i=0; i<= indexController.locations[0].collection.length - 1; i++){ for (int i = 0;
GeoJsonFeature p = indexController.locations[0].collection[i]; i <= indexController.locations[0].features.length - 1;
i++) {
GeoJSONFeature p = indexController.locations[0].features[i]!;
searchResults.add(p); searchResults.add(p);
} }
} }
super.onInit(); super.onInit();
} }
} }

View File

@ -1,6 +1,6 @@
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_typeahead/flutter_typeahead.dart'; import 'package:flutter_typeahead/flutter_typeahead.dart';
import 'package:geojson/geojson.dart'; import 'package:geojson_vi/geojson_vi.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:rogapp/model/destination.dart'; import 'package:rogapp/model/destination.dart';
import 'package:rogapp/pages/destination/destination_controller.dart'; import 'package:rogapp/pages/destination/destination_controller.dart';
@ -48,46 +48,32 @@ class SearchPage extends StatelessWidget {
//title: const CupertinoSearchTextField(), //title: const CupertinoSearchTextField(),
), ),
body: SingleChildScrollView( body: SingleChildScrollView(
child: TypeAheadField( child: TypeAheadField<GeoJSONFeature>(
textFieldConfiguration: TextFieldConfiguration( // textFieldConfiguration: TextFieldConfiguration(
autofocus: true, // autofocus: true,
style: DefaultTextStyle.of(context).style.copyWith( // style: DefaultTextStyle.of(context).style.copyWith(
fontStyle: FontStyle.normal, // fontStyle: FontStyle.normal,
fontSize: 15.0, // fontSize: 15.0,
), // ),
decoration: InputDecoration( // decoration: InputDecoration(
border: const OutlineInputBorder(), // border: const OutlineInputBorder(),
hintText: "検索", // hintText: "検索",
prefixIcon: const Icon(Icons.search), // prefixIcon: const Icon(Icons.search),
suffixIcon: IconButton( // suffixIcon: IconButton(
icon: const Icon(Icons.clear), // icon: const Icon(Icons.clear),
onPressed: () { // onPressed: () {
// clear the text field // // clear the text field
}, // },
), // ),
), // ),
), // ),
suggestionsCallback: (pattern) async { onSelected: (GeoJSONFeature suggestion) {
return searchController.searchResults.where(
(GeoJsonFeature element) => element.properties!["location_name"]
.toString()
.contains(pattern));
//return await
},
itemBuilder: (context, GeoJsonFeature suggestion) {
return ListTile(
title: Text(suggestion.properties!["location_name"]),
subtitle: suggestion.properties!["category"] != null
? Text(suggestion.properties!["category"])
: const Text(""),
//leading: getImage(index),
);
},
onSuggestionSelected: (GeoJsonFeature suggestion) {
indexController.currentFeature.clear(); indexController.currentFeature.clear();
indexController.currentFeature.add(suggestion); indexController.currentFeature.add(suggestion);
DestinationController destinationController = Get.find<DestinationController>(); DestinationController destinationController =
Destination des = destinationController.festuretoDestination(suggestion); Get.find<DestinationController>();
Destination des =
destinationController.festuretoDestination(suggestion);
Get.back(); Get.back();
showModalBottomSheet( showModalBottomSheet(
constraints: constraints:
@ -95,7 +81,28 @@ class SearchPage extends StatelessWidget {
isScrollControlled: true, isScrollControlled: true,
context: context, context: context,
//builder: (context) => BottomSheetWidget(), //builder: (context) => BottomSheetWidget(),
builder: ((context) => BottomSheetNew(destination: des,))); builder: ((context) => BottomSheetNew(
destination: des,
)));
},
suggestionsCallback: (pattern) async {
return searchController.searchResults
.where((GeoJSONFeature element) => element
.properties!["location_name"]
.toString()
.contains(pattern))
.toList();
//return await
},
itemBuilder: (context, GeoJSONFeature suggestion) {
return ListTile(
title: Text(suggestion.properties!["location_name"]),
subtitle: suggestion.properties!["category"] != null
? Text(suggestion.properties!["category"])
: const Text(""),
//leading: getImage(index),
);
}, },
), ),
), ),

View File

@ -0,0 +1,55 @@
import 'dart:async';
import 'package:rogapp/model/destination.dart';
import 'package:rogapp/utils/database_helper.dart';
class DatabaseService {
// Private constructor
DatabaseService._privateConstructor();
// Static instance
static final DatabaseService _instance =
DatabaseService._privateConstructor();
// Factory constructor to return the instance
factory DatabaseService() {
return _instance;
}
// StreamController for updates
final StreamController<List<Destination>> _dbUpdateController =
StreamController<List<Destination>>.broadcast();
// Getter for the stream
Stream<List<Destination>> get destinationUpdatesStream =>
_dbUpdateController.stream;
// Method to fetch destinations
Future<List<Destination>> fetchDestinations() async {
// Your database fetch logic here
List<Destination> destinations = await _fetchFromDb();
_dbUpdateController.add(destinations);
return destinations;
}
// Method to update the database and emit an update through the stream
Future<void> updateDatabase() async {
// Your update logic here
// After updating, fetch the updated list and add it to the stream
fetchDestinations();
}
// Method to fetch data from the database (placeholder)
Future<List<Destination>> _fetchFromDb() async {
// Simulate fetching data with a delay
DatabaseHelper db = DatabaseHelper.instance;
List<Destination> destinations = await db.getDestinations();
return destinations; // Replace with your actual fetch operation
}
// Dispose method to close the stream controller
void dispose() {
_dbUpdateController.close();
}
}

View File

@ -202,13 +202,13 @@ class ExternalService {
'image': "" 'image': ""
}), }),
); );
var vvv = jsonEncode(<String, String>{ // var vvv = jsonEncode(<String, String>{
'team_name': teamname, // 'team_name': teamname,
'cp_number': cp.toString(), // 'cp_number': cp.toString(),
'event_code': eventcode, // 'event_code': eventcode,
'image': res["checkinimage"].toString().replaceAll( // 'image': res["checkinimage"].toString().replaceAll(
'http://localhost:8100', 'http://rogaining.sumasen.net') // 'http://localhost:8100', 'http://rogaining.sumasen.net')
}); // });
// print("--json-- $vvv"); // print("--json-- $vvv");
// print("--- checnin response ${response3.statusCode}----"); // print("--- checnin response ${response3.statusCode}----");
if (response3.statusCode == 200) { if (response3.statusCode == 200) {
@ -300,7 +300,7 @@ class ExternalService {
} }
} }
//} //}
destinationController.resetRogaining(); destinationController.resetRogaining(isgoal: true);
return res2; return res2;
} }

View File

@ -1,32 +1,32 @@
import 'package:geojson/geojson.dart'; // import 'package:geojson/geojson.dart';
import 'package:http/http.dart' as http; // import 'package:http/http.dart' as http;
import '../utils/const.dart'; // import '../utils/const.dart';
class LocationLineService { // class LocationLineService {
static Future<GeoJsonFeature?> loadLocationLines() async { // static Future<GeoJsonFeature?> loadLocationLines() async {
final geo = GeoJson(); // final geo = GeoJson();
GeoJsonFeature? fs; // GeoJsonFeature? fs;
String serverUrl = ConstValues.currentServer(); // String serverUrl = ConstValues.currentServer();
String url = '$serverUrl/api/location_line/'; // String url = '$serverUrl/api/location_line/';
//print('++++++++$url'); // //print('++++++++$url');
final response = await http.get( // final response = await http.get(
Uri.parse(url), // Uri.parse(url),
headers: <String, String>{ // headers: <String, String>{
'Content-Type': 'application/json; charset=UTF-8', // 'Content-Type': 'application/json; charset=UTF-8',
}, // },
); // );
if (response.statusCode == 200) { // if (response.statusCode == 200) {
geo.processedFeatures.listen((fst) { // geo.processedFeatures.listen((fst) {
fs = fst; // fs = fst;
}); // });
await geo.parse(response.body, verbose: true); // await geo.parse(response.body, verbose: true);
return fs; // return fs;
} else { // } else {
throw Exception('Failed to create album.'); // throw Exception('Failed to create album.');
} // }
} // }
} // }

View File

@ -1,33 +1,33 @@
import 'package:geojson/geojson.dart'; // import 'package:geojson/geojson.dart';
import 'package:http/http.dart' as http; // import 'package:http/http.dart' as http;
import '../utils/const.dart'; // import '../utils/const.dart';
class LocationPolygonervice { // class LocationPolygonervice {
static Future<GeoJsonFeature?> loadLocationLines() async { // static Future<GeoJsonFeature?> loadLocationLines() async {
final geo = GeoJson(); // final geo = GeoJson();
GeoJsonFeature? fs; // GeoJsonFeature? fs;
String serverUrl = ConstValues.currentServer(); // String serverUrl = ConstValues.currentServer();
String url = '$serverUrl/api/location_polygon/'; // String url = '$serverUrl/api/location_polygon/';
//print('++++++++$url'); // //print('++++++++$url');
final response = await http.get( // final response = await http.get(
Uri.parse(url), // Uri.parse(url),
headers: <String, String>{ // headers: <String, String>{
'Content-Type': 'application/json; charset=UTF-8', // 'Content-Type': 'application/json; charset=UTF-8',
}, // },
); // );
if (response.statusCode == 200) { // if (response.statusCode == 200) {
geo.processedFeatures.listen((fst) { // geo.processedFeatures.listen((fst) {
fs = fst; // fs = fst;
}); // });
await geo.parse(response.body, verbose: true); // await geo.parse(response.body, verbose: true);
return fs; // return fs;
} else { // } else {
throw Exception('Failed to create album.'); // throw Exception('Failed to create album.');
} // }
} // }
} // }

View File

@ -1,39 +1,13 @@
import 'dart:convert'; import 'dart:convert';
import 'package:geojson_vi/geojson_vi.dart';
import 'package:geojson/geojson.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:http/http.dart' as http; import 'package:http/http.dart' as http;
import 'package:rogapp/pages/destination/destination_controller.dart';
import 'package:rogapp/pages/index/index_controller.dart'; import 'package:rogapp/pages/index/index_controller.dart';
import 'package:rogapp/utils/const.dart'; import 'package:rogapp/utils/const.dart';
class LocationService { class LocationService {
// static Future<GeoJsonFeatureCollection?> loadLocations() async { static Future<GeoJSONFeatureCollection?> loadLocationsFor(
// final IndexController indexController = Get.find<IndexController>();
// String server_url = ConstValues.currentServer();
// String url = "";
// if(indexController.currentUser.length > 0){
// url = '${server_url}/api/location/?is_rog=True';
// }
// else {
// url = '${server_url}/api/location/';
// }
// //String url = 'http://localhost:8100/api/location/';
// final response = await http.get(Uri.parse(url),
// headers: <String, String>{
// 'Content-Type': 'application/json; charset=UTF-8',
// },
// );
// if (response.statusCode == 200) {
// return featuresFromGeoJson(utf8.decode(response.bodyBytes));
// }
// return null;
// }
static Future<GeoJsonFeatureCollection?> loadLocationsFor(
String perfecture, String cat) async { String perfecture, String cat) async {
final IndexController indexController = Get.find<IndexController>(); final IndexController indexController = Get.find<IndexController>();
String url = ""; String url = "";
@ -67,8 +41,8 @@ class LocationService {
); );
if (response.statusCode == 200) { if (response.statusCode == 200) {
GeoJsonFeatureCollection cc = GeoJSONFeatureCollection cc =
await featuresFromGeoJson(utf8.decode(response.bodyBytes)); GeoJSONFeatureCollection.fromJSON(utf8.decode(response.bodyBytes));
//print(cc); //print(cc);
return cc; //featuresFromGeoJson(utf8.decode(response.bodyBytes)); return cc; //featuresFromGeoJson(utf8.decode(response.bodyBytes));
} }
@ -95,48 +69,7 @@ class LocationService {
return ext; return ext;
} }
static Future<GeoJsonFeatureCollection?> loadLocationsSubFor( static Future<GeoJSONFeatureCollection?> loadLocationsBound(
String subperfecture, String cat) async {
final IndexController indexController = Get.find<IndexController>();
String url = "";
String serverUrl = ConstValues.currentServer();
if (cat.isNotEmpty) {
if (indexController.currentUser.isNotEmpty) {
bool rog = indexController.currentUser[0]['user']['is_rogaining'];
String r = rog == true ? 'True' : 'False';
var grp = indexController.currentUser[0]['user']['event_code'];
url = '$serverUrl/api/insubperf?rog=$r&subperf=$subperfecture&cat=$cat';
} else {
url = '$serverUrl/api/insubperf?subperf=$subperfecture&cat=$cat';
}
} else {
if (indexController.currentUser.isNotEmpty) {
bool rog = indexController.currentUser[0]['user']['is_rogaining'];
String r = rog == true ? 'True' : 'False';
var grp = indexController.currentUser[0]['user']['event_code'];
url = '$serverUrl/api/insubperf?rog=$r&subperf=$subperfecture';
} else {
url = '$serverUrl/api/insubperf?subperf=$subperfecture';
}
}
//print('++++++++$url');
final response = await http.get(
Uri.parse(url),
headers: <String, String>{
'Content-Type': 'application/json; charset=UTF-8',
},
);
if (response.statusCode == 200) {
GeoJsonFeatureCollection cc =
await featuresFromGeoJson(utf8.decode(response.bodyBytes));
//print(cc);
return cc; //featuresFromGeoJson(utf8.decode(response.bodyBytes));
}
return null;
}
static Future<GeoJsonFeatureCollection?> loadLocationsBound(
double lat1, double lat1,
double lon1, double lon1,
double lat2, double lat2,
@ -183,13 +116,15 @@ class LocationService {
); );
if (response.statusCode == 500) { if (response.statusCode == 500) {
return GeoJsonFeatureCollection(); //featuresFromGeoJson(utf8.decode(response.bodyBytes)); return null; //featuresFromGeoJson(utf8.decode(response.bodyBytes));
} }
if (response.statusCode == 200) { if (response.statusCode == 200) {
GeoJsonFeatureCollection cc = DestinationController destinationController =
await featuresFromGeoJson(utf8.decode(response.bodyBytes)); Get.find<DestinationController>();
if (cc.collection.isEmpty) { GeoJSONFeatureCollection cc =
GeoJSONFeatureCollection.fromJSON(utf8.decode(response.bodyBytes));
if (cc.features.isEmpty) {
return null; return null;
} else { } else {
//print("---- feature got from server is ${cc.collection[0].properties} ------"); //print("---- feature got from server is ${cc.collection[0].properties} ------");
@ -199,7 +134,7 @@ class LocationService {
return null; return null;
} }
static Future<GeoJsonFeatureCollection?> loadCustomLocations( static Future<GeoJSONFeatureCollection?> loadCustomLocations(
String name, String cat) async { String name, String cat) async {
final IndexController indexController = Get.find<IndexController>(); final IndexController indexController = Get.find<IndexController>();
String url = ""; String url = "";
@ -236,13 +171,13 @@ class LocationService {
); );
if (response.statusCode == 500) { if (response.statusCode == 500) {
return GeoJsonFeatureCollection(); //featuresFromGeoJson(utf8.decode(response.bodyBytes)); return null; //featuresFromGeoJson(utf8.decode(response.bodyBytes));
} }
if (response.statusCode == 200) { if (response.statusCode == 200) {
GeoJsonFeatureCollection cc = GeoJSONFeatureCollection cc =
await featuresFromGeoJson(utf8.decode(response.bodyBytes)); GeoJSONFeatureCollection.fromJSON(utf8.decode(response.bodyBytes));
if (cc.collection.isEmpty) { if (cc.features.isEmpty) {
return null; return null;
} else { } else {
return cc; return cc;

View File

@ -51,7 +51,7 @@ class MatrixService {
Map<String, dynamic> cats = {}; Map<String, dynamic> cats = {};
String url = String url =
"https://maps.googleapis.com/maps/api/directions/json?destination=$destination&mode=$mode&waypoints=$locs&origin=$origin&key=AIzaSyAUBI1ablMKuJwGj2-kSuEhvYxvB1A-mOE"; "https://maps.googleapis.com/maps/api/directions/json?destination=$destination&mode=$mode&waypoints=$locs&origin=$origin&key=AIzaSyCN2xFsqFyadWwpjiFxymrxzS6G1tNzraI";
//print('++++++++$url'); //print('++++++++$url');
final http.Response response = final http.Response response =
await http.get(Uri.parse(url), headers: <String, String>{ await http.get(Uri.parse(url), headers: <String, String>{

View File

@ -44,20 +44,26 @@ class GpsDatabaseHelper {
} }
Future<int> insertGps(GpsData gps) async { Future<int> insertGps(GpsData gps) async {
try {
print("---- try insering ${gps.toMap()}");
Database db = await instance.database; Database db = await instance.database;
int? nextOrder = int? nextOrder =
Sqflite.firstIntValue(await db.rawQuery('SELECT MAX(id) FROM gps')); Sqflite.firstIntValue(await db.rawQuery('SELECT MAX(id) FROM gps'));
nextOrder = nextOrder ?? 0; nextOrder = nextOrder ?? 0;
nextOrder = nextOrder + 1; nextOrder = nextOrder + 1;
gps.id = nextOrder; gps.id = nextOrder;
//print("---- insering ${gps.toMap()}"); print("---- insering ${gps.toMap()}");
int res = await db.insert( int res = await db.insert(
'gps', 'gps',
gps.toMap(), gps.toMap(),
conflictAlgorithm: ConflictAlgorithm.replace, conflictAlgorithm: ConflictAlgorithm.replace,
); );
//print("------ database helper insert $res-----------::::::::"); print("------ database helper insert $res-----------::::::::");
return res; return res;
} catch (err) {
print("------ error $err-----------::::::::");
return -1;
}
} }
Future<List<GpsData>> getGPSData(String team_name, String event_code) async { Future<List<GpsData>> getGPSData(String team_name, String event_code) async {

View File

@ -0,0 +1,162 @@
import 'dart:async';
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import 'package:geolocator/geolocator.dart';
import 'package:rogapp/widgets/debug_widget.dart';
import 'package:flutter_map_location_marker/flutter_map_location_marker.dart';
class LocationController extends GetxController {
// Reactive variable to hold the current position
Rx<Position?> currentPosition = Rx<Position?>(null);
// Subscription to the position stream
StreamSubscription<Position>? positionStream;
final locationMarkerPositionStreamController =
StreamController<LocationMarkerPosition?>.broadcast();
bool isStreamPaused = false;
Stream<LocationMarkerPosition?> get locationMarkerPositionStream =>
locationMarkerPositionStreamController.stream;
@override
void onInit() {
super.onInit();
// Start listening to location updates when the controller is initialized
startPositionStream();
}
void startPositionStream() async {
// Check for location service and permissions before starting the stream
bool serviceEnabled = await Geolocator.isLocationServiceEnabled();
if (!serviceEnabled) {
// Use GetX's context to show a dialog
Get.dialog(
AlertDialog(
title: const Text('Location Services Disabled'),
content: const Text(
'Please enable location services to continue using the app.'),
actions: <Widget>[
TextButton(
child: const Text('OK'),
onPressed: () {
// Close the dialog
Get.back();
// Optionally, you can direct the user to the settings page
// Geolocator.openLocationSettings();
},
),
],
),
barrierDismissible: false, // User must tap button to close dialog
);
return;
}
LocationPermission permission = await Geolocator.checkPermission();
if (permission == LocationPermission.denied) {
permission = await Geolocator.requestPermission();
if (permission == LocationPermission.denied) {
// Show a dialog if permissions are still denied
Get.dialog(
AlertDialog(
title: const Text('Location Permission Denied'),
content: const Text(
'This app requires location permissions to function properly. Please enable location permissions in your device settings.'),
actions: <Widget>[
TextButton(
child: const Text('OK'),
onPressed: () {
// Close the dialog
Get.back();
// Optionally, direct the user to the app settings
// Geolocator.openAppSettings();
},
),
],
),
barrierDismissible: false,
);
return;
}
}
if (permission == LocationPermission.deniedForever) {
// Show a dialog if permissions are permanently denied
Get.dialog(
AlertDialog(
title: const Text('Location Permission Needed'),
content: const Text(
'Location permissions have been permanently denied. Please open app settings to enable location permissions.'),
actions: <Widget>[
TextButton(
child: const Text('Open Settings'),
onPressed: () {
// Close the dialog and open app settings
Get.back();
Geolocator.openAppSettings();
},
),
],
),
barrierDismissible: false,
);
return;
}
// Set up the location options
const locationOptions =
LocationSettings(accuracy: LocationAccuracy.high, distanceFilter: 0);
await positionStream?.cancel();
positionStream =
Geolocator.getPositionStream(locationSettings: locationOptions).listen(
(Position? position) {
if (position != null) {
final LocationMarkerPosition locationMarkerPosition =
LocationMarkerPosition(
latitude: position.latitude,
longitude: position.longitude,
accuracy: position.accuracy);
locationMarkerPositionStreamController.add(locationMarkerPosition);
} else {
locationMarkerPositionStreamController.add(null);
}
},
onError: (e) {
locationMarkerPositionStreamController.addError(e);
},
);
// Resume stream if it was paused previously
if (isStreamPaused) {
isStreamPaused = false;
positionStream!.resume();
}
}
// Method to stop the position stream
void stopPositionStream() {
if (positionStream != null) {
positionStream!.pause();
isStreamPaused = true;
}
}
// Method to resume the position stream
void resumePositionStream() {
if (positionStream != null && isStreamPaused) {
positionStream!.resume();
isStreamPaused = false;
}
}
@override
void onClose() {
// Cancel the position stream subscription when the controller is closed
positionStream?.cancel();
super.onClose();
}
}

View File

@ -129,7 +129,7 @@ class StringValues extends Translations{
'finishing_rogaining' : 'ロゲイニングを終えて', 'finishing_rogaining' : 'ロゲイニングを終えて',
'cp_pls_take_photo' : "CPです。撮影してください。", 'cp_pls_take_photo' : "CPです。撮影してください。",
'take_photo of the clock' : '時計の写真を撮る', 'take_photo of the clock' : '時計の写真を撮る',
'finish_goal': 'フィニッシュゴール', 'finish_goal': 'ゴール完了',
'goal_saved': "目標を保存しました", 'goal_saved': "目標を保存しました",
'goal_added_successfuly' : '目標が正常に追加されました', 'goal_added_successfuly' : '目標が正常に追加されました',
'goal_not_added' : '目標が追加されていません', 'goal_not_added' : '目標が追加されていません',

View File

@ -1,8 +1,8 @@
import 'package:geojson/geojson.dart'; import 'package:geojson_vi/geojson_vi.dart';
import 'package:rogapp/model/destination.dart'; import 'package:rogapp/model/destination.dart';
class TextUtils { class TextUtils {
static String getDisplayTextFeture(GeoJsonFeature f) { static String getDisplayTextFeture(GeoJSONFeature f) {
RegExp regex = RegExp(r'([.]*0)(?!.*\d)'); RegExp regex = RegExp(r'([.]*0)(?!.*\d)');
String txt = ""; String txt = "";
// if(f.properties!["cp"] > 0){ // if(f.properties!["cp"] > 0){

View File

@ -0,0 +1,57 @@
import 'package:flutter/material.dart';
import 'package:rogapp/widgets/GameState/Colors.dart';
class LocationVisitedWidget extends StatelessWidget {
final int count;
final bool minimized;
const LocationVisitedWidget(
{Key? key, required this.count, this.minimized = false})
: super(key: key);
@override
Widget build(BuildContext context) {
if (minimized) {
return Container(
height: 40,
width: 40,
decoration: BoxDecoration(
color: JapaneseColors.mizu,
shape: BoxShape.circle,
),
child: Center(
child: Text(
'$count',
style: TextStyle(
color: Colors.white,
fontWeight: FontWeight.bold,
fontSize: 14,
),
),
),
);
} else {
return Container(
padding: EdgeInsets.symmetric(vertical: 8, horizontal: 8),
decoration: BoxDecoration(
color: JapaneseColors.matcha,
borderRadius: BorderRadius.circular(10),
),
child: Row(
mainAxisSize: MainAxisSize.min,
children: [
Icon(Icons.check_circle_outline, color: Colors.white, size: 24),
SizedBox(width: 8),
Text(
'$count チェックイン', // "X Check-ins" in Japanese
style: TextStyle(
color: Colors.white,
fontWeight: FontWeight.bold,
fontSize: 16),
),
],
),
);
}
}
}

View File

@ -0,0 +1,12 @@
import 'package:flutter/material.dart';
class JapaneseColors {
static const Color mizu = Color(0xFFA4DDED); // Mizu (light blue)
static const Color matcha = Color(0xFFC5E1A5);
static const Color ume = Color(0xFFE1A8A8); // Ume (plum)
static const Color take = Color(0xFF7B8D42); // Take (bamboo)
static const Color sora = Color(0xFFA1CAF1);
static const Color indigo = Color(0xFF264653); // Aizome
static const Color sakuraPink = Color(0xFFFAD2E1); // Sakura-iro
/// Matcha (green tea)
}

View File

@ -0,0 +1,72 @@
import 'package:flutter/material.dart';
import 'package:rogapp/widgets/GameState/Colors.dart';
enum ConnectionStatus { none, mobile, wifi }
class ConnectionStatusIndicator extends StatelessWidget {
final ConnectionStatus connectionStatus;
final bool minimized;
const ConnectionStatusIndicator({
Key? key,
required this.connectionStatus,
this.minimized = false,
}) : super(key: key);
@override
Widget build(BuildContext context) {
Color backgroundColor;
IconData iconData;
String text;
switch (connectionStatus) {
case ConnectionStatus.none:
backgroundColor = JapaneseColors.ume;
iconData = Icons.signal_cellular_off;
text = 'No Connection';
break;
case ConnectionStatus.mobile:
backgroundColor = JapaneseColors.take;
iconData = Icons.signal_cellular_alt;
text = 'Mobile Data';
break;
case ConnectionStatus.wifi:
backgroundColor = JapaneseColors.sora;
iconData = Icons.wifi;
text = 'Wi-Fi';
break;
default:
backgroundColor = Colors.grey; // Fallback color
iconData = Icons.device_unknown;
text = 'Unknown';
}
return Container(
height: minimized ? 40 : null,
width: minimized ? 40 : null,
padding:
minimized ? null : EdgeInsets.symmetric(vertical: 8, horizontal: 16),
decoration: BoxDecoration(
color: backgroundColor,
shape: minimized ? BoxShape.circle : BoxShape.rectangle,
borderRadius: minimized ? null : BorderRadius.circular(10),
),
child: minimized
? Center(
child: Icon(iconData, color: Colors.white, size: 24),
)
: Row(
mainAxisSize: MainAxisSize.min,
children: [
Icon(iconData, color: Colors.white),
SizedBox(width: 8),
Text(
text,
style: TextStyle(
color: Colors.white, fontWeight: FontWeight.bold),
),
],
),
);
}
}

View File

@ -0,0 +1,51 @@
import 'package:flutter/material.dart';
import 'package:rogapp/widgets/GameState/CheckinState.dart';
import 'package:rogapp/widgets/GameState/game_on_off.dart';
class DashboardWidget extends StatelessWidget {
final bool gameStarted;
final int locationsVisited;
final bool isMinimized;
const DashboardWidget({
Key? key,
required this.gameStarted,
required this.locationsVisited,
this.isMinimized = false,
}) : super(key: key);
@override
Widget build(BuildContext context) {
List<Widget> widgets = [
GameStatusIndicator(gameStarted: gameStarted, minimized: isMinimized),
SizedBox(
height: isMinimized ? 0 : 8, width: isMinimized ? 8 : 0), // Spacing
LocationVisitedWidget(count: locationsVisited, minimized: isMinimized),
];
return Container(
padding: EdgeInsets.all(isMinimized ? 8 : 16),
decoration: BoxDecoration(
color: Colors.white,
boxShadow: [
BoxShadow(
color: Colors.grey.withOpacity(0.5),
spreadRadius: 5,
blurRadius: 7,
offset: Offset(0, 3),
),
],
borderRadius: BorderRadius.circular(10),
),
child: isMinimized
? Row(
mainAxisSize: MainAxisSize.min,
children: widgets,
)
: Column(
mainAxisSize: MainAxisSize.min,
children: widgets,
),
);
}
}

View File

@ -0,0 +1,55 @@
import 'package:flutter/material.dart';
import 'package:rogapp/widgets/GameState/Colors.dart';
class GameStatusIndicator extends StatelessWidget {
final bool gameStarted;
final bool minimized;
const GameStatusIndicator(
{Key? key, required this.gameStarted, this.minimized = true})
: super(key: key);
@override
Widget build(BuildContext context) {
// Icons to show based on the game status
IconData iconData =
gameStarted ? Icons.stop_circle : Icons.play_circle_filled;
// Text to show based on the game status
String text = gameStarted ? 'ゲーム開始' : 'ゲーム未開始';
// Layout for minimized view
if (minimized) {
return Container(
height: 40, // Square size
width: 40, // Square size
decoration: BoxDecoration(
color:
gameStarted ? JapaneseColors.indigo : JapaneseColors.sakuraPink,
shape: BoxShape
.circle, // Making it circle when minimized for a more distinct look
),
child: Icon(iconData, color: Colors.white),
);
}
// Layout for expanded view
return Container(
padding: EdgeInsets.all(12),
decoration: BoxDecoration(
color: gameStarted ? JapaneseColors.indigo : JapaneseColors.sakuraPink,
borderRadius: BorderRadius.circular(10),
),
child: Row(
mainAxisSize: MainAxisSize.min,
children: [
Icon(iconData, color: Colors.white),
SizedBox(width: 8),
Text(
text,
style: TextStyle(color: Colors.white, fontWeight: FontWeight.bold),
),
],
),
);
}
}

View File

@ -10,12 +10,9 @@ class BaseLayer extends StatelessWidget {
return TileLayer( return TileLayer(
urlTemplate: "https://cyberjapandata.gsi.go.jp/xyz/std/{z}/{x}/{y}.png", urlTemplate: "https://cyberjapandata.gsi.go.jp/xyz/std/{z}/{x}/{y}.png",
tileProvider: FMTC.instance('OpenStreetMap (A)').getTileProvider( tileProvider: FMTC.instance('OpenStreetMap (A)').getTileProvider(
FMTCTileProviderSettings( settings: FMTCTileProviderSettings(
behavior: CacheBehavior.values behavior: CacheBehavior.values.byName('cacheFirst'),
.byName('cacheFirst'), cachedValidDuration: const Duration(days: 14),
cachedValidDuration: const Duration(
days: 14
),
), ),
), ),
); );

View File

@ -1,11 +1,8 @@
import 'package:geojson_vi/geojson_vi.dart';
import 'package:geojson/geojson.dart';
import 'package:get/get_state_manager/get_state_manager.dart'; import 'package:get/get_state_manager/get_state_manager.dart';
class BottomSheetController extends GetxController { class BottomSheetController extends GetxController {
List<GeoJSONFeature>? currentFeature = <GeoJSONFeature>[];
List<GeoJsonFeature>? currentFeature = <GeoJsonFeature>[];
BottomSheetController({this.currentFeature}); BottomSheetController({this.currentFeature});
} }

View File

@ -1,7 +1,6 @@
import 'dart:ffi';
import 'dart:ui' as ui; import 'dart:ui' as ui;
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:geojson/geojson.dart'; import 'package:geojson_vi/geojson_vi.dart';
import 'package:geolocator/geolocator.dart'; import 'package:geolocator/geolocator.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:image_picker/image_picker.dart'; import 'package:image_picker/image_picker.dart';
@ -11,14 +10,12 @@ import 'package:rogapp/model/destination.dart';
import 'package:rogapp/pages/camera/camera_page.dart'; import 'package:rogapp/pages/camera/camera_page.dart';
import 'package:rogapp/pages/destination/destination_controller.dart'; import 'package:rogapp/pages/destination/destination_controller.dart';
import 'package:rogapp/pages/index/index_controller.dart'; import 'package:rogapp/pages/index/index_controller.dart';
import 'package:rogapp/routes/app_pages.dart';
import 'package:rogapp/services/external_service.dart'; import 'package:rogapp/services/external_service.dart';
import 'package:rogapp/utils/const.dart'; import 'package:rogapp/utils/const.dart';
import 'package:rogapp/utils/database_helper.dart'; import 'package:rogapp/utils/database_helper.dart';
import 'package:rogapp/utils/text_util.dart'; import 'package:rogapp/utils/text_util.dart';
import 'package:rogapp/widgets/bottom_sheet_controller.dart'; import 'package:rogapp/widgets/bottom_sheet_controller.dart';
import 'package:rogapp/widgets/debug_widget.dart'; import 'package:rogapp/widgets/debug_widget.dart';
import 'package:sqflite/sqflite.dart';
import 'package:url_launcher/url_launcher.dart'; import 'package:url_launcher/url_launcher.dart';
class BottomSheetNew extends GetView<BottomSheetController> { class BottomSheetNew extends GetView<BottomSheetController> {
@ -34,8 +31,8 @@ class BottomSheetNew extends GetView<BottomSheetController> {
Image getImage() { Image getImage() {
String serverUrl = ConstValues.currentServer(); String serverUrl = ConstValues.currentServer();
if (indexController.rogMode == 1) { if (indexController.rogMode == 1) {
//print("----- rogaining mode 1");
if (indexController.currentDestinationFeature.isEmpty || if (indexController.currentDestinationFeature.isEmpty ||
indexController.currentDestinationFeature[0].photos! == "") { indexController.currentDestinationFeature[0].photos! == "") {
return const Image(image: AssetImage('assets/images/empty_image.png')); return const Image(image: AssetImage('assets/images/empty_image.png'));
@ -65,8 +62,8 @@ class BottomSheetNew extends GetView<BottomSheetController> {
} }
} }
} else { } else {
GeoJsonFeature<dynamic> gf = indexController.currentFeature[0]; GeoJSONFeature gf = indexController.currentFeature[0];
//print("=== photo sss ${gf.properties!["photos"]}"); print("=== photo sss ${gf.properties!["photos"]}");
if (gf.properties!["photos"] == null || gf.properties!["photos"] == "") { if (gf.properties!["photos"] == null || gf.properties!["photos"] == "") {
return const Image(image: AssetImage('assets/images/empty_image.png')); return const Image(image: AssetImage('assets/images/empty_image.png'));
} else { } else {
@ -113,8 +110,140 @@ class BottomSheetNew extends GetView<BottomSheetController> {
} }
} }
Widget getActionButton(BuildContext context, Destination destination) {
assert(() {
print("getActionButton ${destinationController.rogainingCounted.value}");
print("getActionButton ${destinationController.distanceToStart()}");
print("getActionButton ${destination.cp}");
print("getActionButton ${DestinationController.ready_for_goal}");
return true;
}());
// ...2024-04-03 Akira デバッグモードのみ出力するようにした。
Destination cdest = destinationController
.festuretoDestination(indexController.currentFeature[0]);
var distance = const Distance();
double distanceToDest = distance.as(
LengthUnit.Meter,
LatLng(
destinationController.currentLat, destinationController.currentLon),
LatLng(cdest.lat!, cdest.lon!));
if (destinationController.rogainingCounted.value == true &&
destinationController.distanceToStart() <= 500 &&
destination.cp == -1 &&
DestinationController.ready_for_goal == true) {
//goal
return ElevatedButton(
style: ElevatedButton.styleFrom(backgroundColor: Colors.red),
onPressed: destinationController.rogainingCounted.value == true &&
destinationController.distanceToStart() <= 500 &&
destination.cp == -1 &&
DestinationController.ready_for_goal == true
? () async {
destinationController.isAtGoal.value = true;
destinationController.photos.clear();
await showModalBottomSheet(
constraints: BoxConstraints.loose(
ui.Size(Get.width, Get.height * 0.75)),
context: Get.context!,
isScrollControlled: true,
builder: ((context) => CameraPage(
destination: destination,
))).whenComplete(() {
destinationController.skipGps = false;
destinationController.chekcs = 0;
destinationController.isAtGoal.value = false;
});
}
: null,
child: const Text(
"ロゲイニングを終える",
style: TextStyle(color: Colors.white),
));
} else if (distanceToDest <=
destinationController.getForcedChckinDistance(destination)) {
//start
return ElevatedButton(
style: ElevatedButton.styleFrom(
backgroundColor: Theme.of(context).colorScheme.secondary,
),
onPressed: () async {
// Check conditions to show confirmation dialog
if (destinationController.isInRog.value == false &&
destination.cp == -1 &&
destinationController.rogainingCounted.value == false) {
print("counted ${destinationController.rogainingCounted.value}");
// Show confirmation dialog
Get.dialog(
AlertDialog(
title: const Text("確認"), //confirm
content: const Text(
"ロゲを開始すると、今までのロゲデータが全てクリアされます。本当に開始しますか?"), //are you sure
actions: <Widget>[
TextButton(
child: const Text("いいえ"), //no
onPressed: () {
Get.back(); // Close the dialog
},
),
TextButton(
child: const Text("はい"), //yes
onPressed: () async {
// Clear data and start game logic here
destinationController.isInRog.value = true;
destinationController.resetRogaining();
destinationController.addToRogaining(
destinationController.currentLat,
destinationController.currentLon,
destination.location_id!,
);
saveGameState();
await ExternalService().startRogaining();
Get.back(); // Close the dialog and potentially navigate away
},
),
],
),
barrierDismissible:
false, // User must tap a button to close the dialog
);
} else if (destinationController.isInRog.value == true &&
destination.cp != -1) {
//print("counted ${destinationController.rogainingCounted.value}");
// Existing logic for other conditions
Get.back();
await destinationController.callforCheckin(destination);
} else {
return;
}
},
child: Text(
destination.cp == -1 &&
destinationController.isInRog.value == false &&
destinationController.rogainingCounted.value == false
? "ロゲ開始"
: destinationController.isInRog.value == true &&
destination.cp == -1
? "ゲーム中"
: isAlreadyCheckedIn == true
? "ゲーム中"
: destinationController.isInRog.value == true
? "チェックイン"
: "始まっていない",
style: TextStyle(color: Theme.of(context).colorScheme.onSecondary),
),
);
}
return Container();
}
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
//print("to start ${destinationController.distanceToStart()}");
destinationController.skipGps = true; destinationController.skipGps = true;
// print('--- c use --- ${indexController.currentUser[0].values}'); // print('--- c use --- ${indexController.currentUser[0].values}');
// print('---- rog_mode ----- ${indexController.rogMode.value} -----'); // print('---- rog_mode ----- ${indexController.rogMode.value} -----');
@ -124,261 +253,6 @@ class BottomSheetNew extends GetView<BottomSheetController> {
return detailsSheet(context); return detailsSheet(context);
} }
// Show destination detais
// SingleChildScrollView destinationSheet(BuildContext context) {
// // print(
// // '---- currentDestinationFeature ----- ${indexController.currentDestinationFeature[0].name} -----');
// return SingleChildScrollView(
// child: Column(
// children: [
// Padding(
// padding: const EdgeInsets.all(8.0),
// child: Row(
// children: [
// MaterialButton(
// onPressed: () {
// Get.back();
// //destinationController.makePrevious(indexController.currentDestinationFeature[0]);
// },
// color: Colors.blue,
// textColor: Colors.white,
// padding: const EdgeInsets.all(16),
// shape: const CircleBorder(),
// child: const Icon(
// Icons.arrow_back_ios,
// size: 14,
// ),
// ),
// Expanded(
// child: Container(
// alignment: Alignment.center,
// child: Obx(() => indexController.currentUser.isNotEmpty
// ? Text(
// "${TextUtils.getDisplayText(indexController.currentDestinationFeature[0])} : ${TextUtils.getDisplayText(indexController.currentDestinationFeature[0])} : ${indexController.currentDestinationFeature[0].name!}",
// style: const TextStyle(
// fontSize: 15.0,
// fontWeight: FontWeight.bold,
// ),
// )
// : Text(
// indexController.currentDestinationFeature[0].name!,
// style: const TextStyle(
// fontSize: 15.0,
// fontWeight: FontWeight.bold,
// ),
// )),
// ),
// ),
// ],
// ),
// ),
// Row(
// children: [
// Expanded(
// child: SizedBox(
// height: 260.0,
// child: Obx(() => getImage()),
// )),
// ],
// ),
// Row(
// mainAxisAlignment: MainAxisAlignment.spaceAround,
// children: [
// Obx(
// () => indexController.currentDestinationFeature.isNotEmpty &&
// destinationController.isInCheckin.value == true &&
// destinationController.isAtStart.value == false
// ? Row(
// children: [
// ElevatedButton(
// onPressed: () {
// if (indexController.currentDestinationFeature[0]
// .checkedin ==
// null ||
// indexController.currentDestinationFeature[0]
// .checkedin ==
// false) {
// if (indexController
// .currentDestinationFeature[0]
// .hidden_location ==
// 0) {
// destinationController.skipGps = false;
// destinationController.isPhotoShoot.value =
// true;
// Get.back();
// } else {
// destinationController.makeCheckin(
// indexController
// .currentDestinationFeature[0],
// true,
// "");
// if (indexController
// .currentDestinationFeature[0].cp !=
// -1) {
// destinationController
// .rogainingCounted.value = true;
// }
// }
// } else {
// destinationController.makeCheckin(
// indexController
// .currentDestinationFeature[0],
// false,
// "");
// }
// //Get.back();
// },
// child: Text(
// //Checkin
// indexController.currentDestinationFeature[0]
// .checkedin ==
// null ||
// indexController
// .currentDestinationFeature[0]
// .checkedin ==
// false
// ? "チェックイン"
// : "チェックアウト")),
// ],
// )
// : Container(),
// ),
// Obx(
// () => destinationController.isAtStart.value == true
// ? ElevatedButton(
// onPressed: () {
// destinationController.isInRog.value = true;
// destinationController.addToRogaining(
// destinationController.currentLat,
// destinationController.currentLon,
// indexController
// .currentDestinationFeature[0].location_id!);
// saveGameState();
// ExternalService()
// .startRogaining()
// .then((value) => Get.back());
// },
// child: Text(
// // start
// indexController.currentDestinationFeature[0]
// .checkedin !=
// null ||
// indexController.currentDestinationFeature[0]
// .checkedin ==
// true
// ? "ロゲイニングを開始"
// : "間違った目的地..."))
// : Container(),
// ),
// Obx(
// () => destinationController.isAtGoal.value == true &&
// destinationController.rogainingCounted.value == true
// ? ElevatedButton(
// onPressed: () {
// Get.toNamed(AppPages.CAMERA_PAGE);
// Get.back();
// },
// child: Text(
// //goal
// indexController.currentDestinationFeature[0]
// .checkedin !=
// null ||
// indexController.currentDestinationFeature[0]
// .checkedin ==
// true
// ? "ロゲイニングを終える"
// : "間違った目的地 ..."))
// : Container(),
// ),
// ],
// ),
// Obx(
// () => indexController.currentDestinationFeature[0].address !=
// null &&
// indexController
// .currentDestinationFeature[0].address!.isNotEmpty
// ? getDetails(context, "address".tr,
// indexController.currentDestinationFeature[0].address! ?? '')
// : const SizedBox(
// width: 0.0,
// height: 0,
// ),
// ),
// Obx(
// () => indexController.currentDestinationFeature[0].phone != null &&
// indexController
// .currentDestinationFeature[0].phone!.isNotEmpty
// ? getDetails(context, "telephone".tr,
// indexController.currentDestinationFeature[0].phone! ?? '')
// : const SizedBox(
// width: 0.0,
// height: 0,
// ),
// ),
// Obx(
// () => indexController.currentDestinationFeature[0].email != null &&
// indexController
// .currentDestinationFeature[0].email!.isNotEmpty
// ? getDetails(context, "email".tr,
// indexController.currentDestinationFeature[0].email! ?? '')
// : const SizedBox(
// width: 0.0,
// height: 0,
// ),
// ),
// Obx(
// () => indexController.currentDestinationFeature[0].webcontents !=
// null &&
// indexController
// .currentDestinationFeature[0].webcontents!.isNotEmpty
// ? getDetails(
// context,
// "web".tr,
// indexController.currentDestinationFeature[0].webcontents! ??
// '',
// isurl: true)
// : const SizedBox(
// width: 0.0,
// height: 0,
// ),
// ),
// Obx(
// () => indexController.currentDestinationFeature[0].videos != null &&
// indexController
// .currentDestinationFeature[0].videos!.isNotEmpty
// ? getDetails(context, "video".tr,
// indexController.currentDestinationFeature[0].videos! ?? '',
// isurl: true)
// : const SizedBox(
// width: 0.0,
// height: 0,
// ),
// ),
// const SizedBox(
// height: 20.0,
// ),
// // Obx(() =>
// // //wantToGo(context),
// // FutureBuilder<Widget>(
// // future: wantToGo(context),
// // builder: (context, snapshot) {
// // return Container(
// // child: snapshot.data,
// // );
// // },
// // ),
// // ),
// const SizedBox(
// height: 60.0,
// )
// ],
// ),
// );
// }
Future<bool> isDestinationCheckedIn(Destination d) async { Future<bool> isDestinationCheckedIn(Destination d) async {
DatabaseHelper db = DatabaseHelper.instance; DatabaseHelper db = DatabaseHelper.instance;
List<Destination> ds = await db.getDestinationByLatLon(d.lat!, d.lon!); List<Destination> ds = await db.getDestinationByLatLon(d.lat!, d.lon!);
@ -462,79 +336,13 @@ class BottomSheetNew extends GetView<BottomSheetController> {
Row( Row(
mainAxisAlignment: MainAxisAlignment.spaceAround, mainAxisAlignment: MainAxisAlignment.spaceAround,
children: [ children: [
// Obx( // Finish or Goal
// () => indexController getActionButton(context, destination),
// .currentDestinationFeature.isNotEmpty &&
// indexController
// .currentDestinationFeature[0].cp ==
// -1 &&
// indexController.currentDestinationFeature[0]
// .checkedin ==
// false &&
// destinationController.isAtStart.value == true
// ? ElevatedButton(
// onPressed: () async {
// await destinationController
// .resetRogaining();
// //print("~~~~ start button ~~~~");
// destinationController.isInRog.value = true;
// destinationController.addToRogaining(
// destinationController.currentLat,
// destinationController.currentLon,
// indexController
// .currentDestinationFeature[0]
// .location_id!);
// saveGameState();
// ExternalService()
// .startRogaining()
// .then((value) {
// Get.back();
// });
// },
// child: Text(
// // start
// indexController
// .currentDestinationFeature[
// 0]
// .checkedin !=
// null ||
// indexController
// .currentDestinationFeature[
// 0]
// .checkedin ==
// true
// ? "ロゲイニングを開始"
// : "間違った目的地..."))
// : Container(),
// ),
destinationController.rogainingCounted.value == true &&
destinationController.distanceToStart() <=
500 &&
destination.cp == -1
? ElevatedButton(
onPressed: () async {
destinationController.isAtGoal.value = true;
destinationController.photos.clear();
await showModalBottomSheet(
constraints: BoxConstraints.loose(ui.Size(
Get.width, Get.height * 0.75)),
context: Get.context!,
isScrollControlled: true,
builder: ((context) => CameraPage(
destination: destination,
))).whenComplete(() {
destinationController.skipGps = false;
destinationController.chekcs = 0;
destinationController.isAtGoal.value =
false;
});
},
child: Text("ロゲイニングを終える"))
: Container(),
//remove checkin //remove checkin
isAlreadyCheckedIn == true && destination.cp != -1 isAlreadyCheckedIn == true && destination.cp != -1
? ElevatedButton( ? ElevatedButton(
style: ElevatedButton.styleFrom(
backgroundColor: Colors.blueAccent),
onPressed: () async { onPressed: () async {
await destinationController await destinationController
.removeCheckin(destination.cp!.toInt()); .removeCheckin(destination.cp!.toInt());
@ -542,35 +350,11 @@ class BottomSheetNew extends GetView<BottomSheetController> {
.deleteDestination(destination); .deleteDestination(destination);
Get.back(); Get.back();
}, },
child: const Text("チェックイン取消")) child: const Text(
"チェックイン取消",
style: TextStyle(color: Colors.white),
)) //remove checkin
: Container(), : Container(),
// Obx(
// () => destinationController.rogainingCounted.value ==
// false &&
// destination.cp == -1 &&
// destinationController.distanceToStart() <= 500
// ? ElevatedButton(
// onPressed: () {
// Get.toNamed(AppPages.CAMERA_PAGE);
// Get.back();
// },
// child: Text(
// //goal
// indexController
// .currentDestinationFeature[
// 0]
// .checkedin !=
// null ||
// indexController
// .currentDestinationFeature[
// 0]
// .checkedin ==
// true
// ? "ロゲイニングを終える"
// : "間違った目的地 ..."))
// : Container(),
// ),
], ],
), ),
Row( Row(
@ -582,11 +366,12 @@ class BottomSheetNew extends GetView<BottomSheetController> {
.colorScheme .colorScheme
.onPrimaryContainer), .onPrimaryContainer),
onPressed: () async { onPressed: () async {
// print(
// "dist to start ${destinationController.distanceToStart()}");
Get.back(); Get.back();
//print("---- go to ----"); //print("---- go to ----");
GeoJsonFeature<GeoJsonMultiPoint> mp = // GeoJSONMultiPoint mp = indexController
indexController.currentFeature[0] // .currentFeature[0] as GeoJSONMultiPoint;
as GeoJsonFeature<GeoJsonMultiPoint>;
Position position = Position position =
await Geolocator.getCurrentPosition( await Geolocator.getCurrentPosition(
desiredAccuracy: desiredAccuracy:
@ -598,14 +383,12 @@ class BottomSheetNew extends GetView<BottomSheetController> {
lon: position.longitude); lon: position.longitude);
Destination tp = Destination( Destination tp = Destination(
lat: mp.geometry!.geoSerie!.geoPoints[0] lat: destination.lat, lon: destination.lon);
.latitude,
lon: mp.geometry!.geoSerie!.geoPoints[0]
.longitude);
destinationController destinationController
.destinationMatrixFromCurrentPoint([ds, tp]); .destinationMatrixFromCurrentPoint([ds, tp]);
}, },
//go here
child: Text( child: Text(
"ここへ行く", "ここへ行く",
style: TextStyle( style: TextStyle(
@ -617,61 +400,6 @@ class BottomSheetNew extends GetView<BottomSheetController> {
), ),
// forced start / checkin // forced start / checkin
distanceToDest <=
destinationController
.getForcedChckinDistance(destination)
? Obx(() => ElevatedButton(
style: ElevatedButton.styleFrom(
backgroundColor: Theme.of(context)
.colorScheme
.secondary),
onPressed: () async {
//print("~~~~ manual checkin button ~~~~");
if (destination.cp == -1 &&
destinationController.isInRog.value ==
false &&
destinationController
.rogainingCounted.value ==
false) {
destinationController.isInRog.value = true;
destinationController.addToRogaining(
destinationController.currentLat,
destinationController.currentLon,
destination.location_id!);
saveGameState();
ExternalService()
.startRogaining()
.then((value) => Get.back());
} else {
if (destination.cp == -1) {
return;
}
Get.back();
await destinationController
.callforCheckin(destination);
}
},
child: Text(
destination.cp == -1 &&
destinationController
.isInRog.value ==
false &&
destinationController
.rogainingCounted.value ==
false
? "ロゲ開始"
: destinationController.isInRog.value ==
true &&
destination.cp == -1
? "ゲーム中"
: isAlreadyCheckedIn == true
? "ゲーム中"
: "チェックイン",
style: TextStyle(
color: Theme.of(context)
.colorScheme
.onSecondary))))
: Container(),
], ],
), ),
Row( Row(

View File

@ -0,0 +1,34 @@
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import 'package:rogapp/pages/destination/destination_controller.dart';
class CurrentPosition extends StatefulWidget {
const CurrentPosition({super.key});
@override
State<CurrentPosition> createState() => _CurrentPositionState();
}
class _CurrentPositionState extends State<CurrentPosition> {
final DestinationController destinationController =
Get.find<DestinationController>();
@override
Widget build(BuildContext context) {
return Container(
width: 40,
height: 40,
decoration: BoxDecoration(
color: Colors.grey, borderRadius: BorderRadius.circular(20.0)),
child: IconButton(
onPressed: () {
destinationController.centerMapToCurrentLocation();
},
icon: const Icon(
Icons.location_searching,
color: Colors.white,
),
),
);
}
}

View File

@ -0,0 +1,210 @@
import 'dart:ffi';
import 'dart:math';
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import 'package:rogapp/model/destination.dart';
import 'package:rogapp/pages/destination/destination_controller.dart';
import 'package:rogapp/pages/index/index_controller.dart';
import 'package:rogapp/services/DatabaseService.dart';
import 'package:rogapp/utils/database_helper.dart';
import 'package:rogapp/widgets/GameState/CheckinState.dart';
import 'package:rogapp/widgets/GameState/ConnectionStatus.dart';
import 'package:rogapp/widgets/GameState/DashboardWidget.dart';
import 'package:rogapp/widgets/GameState/game_on_off.dart';
class GameStateManager {
static final GameStateManager _instance = GameStateManager._internal();
factory GameStateManager() {
return _instance;
}
GameStateManager._internal();
List<String> _logs = [];
List<VoidCallback> _listeners = [];
List<String> get logs => _logs;
void addLog(String log) {
_logs.add(log);
_notifyListeners(); // Notify all listeners
}
void clearLogs() {
_logs.clear();
_notifyListeners(); // Notify all listeners
}
void addListener(VoidCallback listener) {
_listeners.add(listener);
}
void removeListener(VoidCallback listener) {
_listeners.remove(listener);
}
void _notifyListeners() {
for (var listener in _listeners) {
listener();
}
}
}
class GameStateWidget extends StatefulWidget {
const GameStateWidget({super.key});
@override
State<GameStateWidget> createState() => _GameStateWidgetState();
}
class _GameStateWidgetState extends State<GameStateWidget> {
final GameStateManager gameStateManager = GameStateManager();
final IndexController indexController = Get.find<IndexController>();
final DestinationController destinationController =
Get.find<DestinationController>();
@override
void initState() {
super.initState();
gameStateManager.addListener(_updateLogs);
}
@override
void dispose() {
gameStateManager.removeListener(_updateLogs);
super.dispose();
}
void _updateLogs() {
Future.delayed(Duration.zero, () {
if (mounted) {
setState(() {});
}
});
}
void toggleExpanded() {
setState(() {
isExpanded = !isExpanded;
});
}
void clearLogs() {
gameStateManager.clearLogs();
}
bool isExpanded = false;
@override
Widget build(BuildContext context) {
final DatabaseService dbService = DatabaseService();
return Container(
width: MediaQuery.of(context).size.width,
decoration: BoxDecoration(color: Colors.black12),
child: GestureDetector(
onTap: toggleExpanded,
child: AnimatedContainer(
duration: const Duration(milliseconds: 200),
color: isExpanded ? Colors.black54 : Colors.black12,
height: isExpanded ? 160.0 : 48.0, // Adjust sizes as needed
child: Column(
children: [
// Top bar with clear button
if (isExpanded)
Container(
padding: EdgeInsets.symmetric(horizontal: 10.0),
color: Colors.blueGrey, // Adjust color as needed
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
crossAxisAlignment: CrossAxisAlignment.center,
children: [
Text('ゲームステータス', style: TextStyle(color: Colors.white)),
IconButton(
icon: Icon(Icons.clear, color: Colors.white),
onPressed: toggleExpanded,
),
],
),
),
// Log messages
Expanded(
child: SingleChildScrollView(
child: Wrap(
alignment: WrapAlignment.spaceEvenly,
children: [
Obx(() => Padding(
padding: const EdgeInsets.all(4.0),
child: GameStatusIndicator(
gameStarted: destinationController.isInRog.value,
minimized: !isExpanded,
),
)),
Padding(
padding: const EdgeInsets.all(4.0),
child: StreamBuilder<List<Destination>>(
stream: dbService.destinationUpdatesStream,
builder: (context, snapshot) {
if (snapshot.connectionState ==
ConnectionState.waiting) {
return const CircularProgressIndicator();
} else if (snapshot.hasError) {
return LocationVisitedWidget(
count: 0,
minimized: !isExpanded,
);
} else if (snapshot.hasData) {
return LocationVisitedWidget(
count: snapshot.data!.length,
minimized: !isExpanded,
);
} else {
return LocationVisitedWidget(
count: 0,
minimized: !isExpanded,
);
}
},
),
// child: LocationVisitedWidget(
// count:
// minimized: !isExpanded,
// ),
),
Padding(
padding: const EdgeInsets.all(4.0),
child: Obx(() => ConnectionStatusIndicator(
connectionStatus: (indexController
.connectionStatusName.value ==
"wifi" ||
indexController
.connectionStatusName.value ==
"mobile")
? indexController.connectionStatusName.value ==
"wifi"
? ConnectionStatus.wifi
: ConnectionStatus.mobile
: ConnectionStatus.none,
minimized: !isExpanded)),
) // Expanded view
],
),
// child: Obx(
// () => DashboardWidget(
// gameStarted: destinationController.isInRog.value,
// locationsVisited: 3,
// isMinimized: false,
// ),
),
),
],
),
),
),
);
}
}

View File

@ -1,5 +1,5 @@
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:geojson/geojson.dart'; import 'package:geojson_vi/geojson_vi.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:rogapp/model/destination.dart'; import 'package:rogapp/model/destination.dart';
import 'package:rogapp/pages/destination/destination_controller.dart'; import 'package:rogapp/pages/destination/destination_controller.dart';
@ -22,16 +22,15 @@ class _ListWidgetState extends State<ListWidget> {
Get.find<DestinationController>(); Get.find<DestinationController>();
Image getImage(int index) { Image getImage(int index) {
if (indexController.locations[0].collection[index].properties!["photos"] == if (indexController.locations[0].features[index]!.properties!["photos"] ==
null || null ||
indexController.locations[0].collection[index].properties!["photos"] == indexController.locations[0].features[index]!.properties!["photos"] ==
"") { "") {
return const Image(image: AssetImage('assets/images/empty_image.png')); return const Image(image: AssetImage('assets/images/empty_image.png'));
} else { } else {
//print("==== photo index is $index ==="); //print("==== photo index is $index ===");
String serverUrl = ConstValues.currentServer(); String serverUrl = ConstValues.currentServer();
GeoJsonFeature<dynamic> gf = GeoJSONFeature gf = indexController.locations[0].features[index]!;
indexController.locations[0].collection[index];
String photo = gf.properties!["photos"]; String photo = gf.properties!["photos"];
return Image( return Image(
image: NetworkImage('$serverUrl/media/compressed/$photo'), image: NetworkImage('$serverUrl/media/compressed/$photo'),
@ -43,7 +42,7 @@ class _ListWidgetState extends State<ListWidget> {
} }
} }
void changeCurrentFeature(GeoJsonFeature fs) { void changeCurrentFeature(GeoJSONFeature fs) {
if (indexController.currentFeature.isNotEmpty) { if (indexController.currentFeature.isNotEmpty) {
indexController.currentFeature.clear(); indexController.currentFeature.clear();
} }
@ -55,14 +54,14 @@ class _ListWidgetState extends State<ListWidget> {
super.initState(); super.initState();
} }
Destination createDestination(GeoJsonFeature feature) { Destination createDestination(GeoJSONFeature feature) {
final props = feature.properties; final props = feature.properties;
GeoJsonMultiPoint pt = feature.geometry; GeoJSONMultiPoint pt = feature.geometry as GeoJSONMultiPoint;
return Destination( return Destination(
cp: props!['cp'], cp: props!['cp'],
lat: pt.geoSerie!.geoPoints.first.latitude, lat: pt.coordinates[0][1],
lon: pt.geoSerie!.geoPoints.first.longitude, lon: pt.coordinates[0][0],
); );
} }
@ -72,7 +71,7 @@ class _ListWidgetState extends State<ListWidget> {
lat: indexController.currentLat, lon: indexController.currentLon); lat: indexController.currentLat, lon: indexController.currentLon);
//Destination dest1 = createDestination(indexController.locations[0].collection[0]); //Destination dest1 = createDestination(indexController.locations[0].collection[0]);
Destination dest2 = Destination dest2 =
createDestination(indexController.locations[0].collection[i]); createDestination(indexController.locations[0].features[i]!);
// Get the distance between these two destinations // Get the distance between these two destinations
final res = await MatrixService.getDestinations([desCurr, dest2]); final res = await MatrixService.getDestinations([desCurr, dest2]);
@ -83,9 +82,9 @@ class _ListWidgetState extends State<ListWidget> {
Future<void> _pullRefresh() async { Future<void> _pullRefresh() async {
//print("pull to refesh"); //print("pull to refesh");
indexController.locations[0].collection.sort((a, b) => indexController.locations[0].features.sort((a, b) =>
(a.properties!['cp'] as Comparable) (a!.properties!['cp'] as Comparable)
.compareTo(b.properties!['cp'] as Comparable)); .compareTo(b!.properties!['cp'] as Comparable));
setState(() {}); setState(() {});
} }
@ -96,12 +95,12 @@ class _ListWidgetState extends State<ListWidget> {
? RefreshIndicator( ? RefreshIndicator(
onRefresh: _pullRefresh, onRefresh: _pullRefresh,
child: ListView.builder( child: ListView.builder(
itemCount: indexController.locations[0].collection.length, itemCount: indexController.locations[0].features.length,
shrinkWrap: true, shrinkWrap: true,
itemBuilder: (_, index) { itemBuilder: (_, index) {
bool isFound = false; bool isFound = false;
for (Destination d in destinationController.destinations) { for (Destination d in destinationController.destinations) {
if (indexController.locations[0].collection[index] if (indexController.locations[0].features[index]!
.properties!['location_id'] == .properties!['location_id'] ==
d.location_id) { d.location_id) {
isFound = true; isFound = true;
@ -113,8 +112,8 @@ class _ListWidgetState extends State<ListWidget> {
selected: isFound, selected: isFound,
selectedTileColor: Colors.yellow.shade200, selectedTileColor: Colors.yellow.shade200,
onTap: () { onTap: () {
GeoJsonFeature gf = GeoJSONFeature gf =
indexController.locations[0].collection[index]; indexController.locations[0].features[index]!;
Destination des = Destination des =
destinationController.festuretoDestination(gf); destinationController.festuretoDestination(gf);
changeCurrentFeature(gf); changeCurrentFeature(gf);
@ -129,29 +128,27 @@ class _ListWidgetState extends State<ListWidget> {
))); )));
}, },
leading: getImage(index), leading: getImage(index),
title: indexController.locations[0].collection[index] title: indexController.locations[0].features[index]!
.properties!['location_name'] != .properties!['location_name'] !=
null null
? Text(indexController.locations[0] ? Text(indexController.locations[0].features[index]!
.collection[index].properties!['location_name'] .properties!['location_name']
.toString()) .toString())
: const Text(""), : const Text(""),
subtitle: indexController.locations[0].collection[index] subtitle: indexController.locations[0].features[index]!
.properties!['category'] != .properties!['category'] !=
null null
? Text(indexController.locations[0] ? Text(indexController.locations[0].features[index]!
.collection[index].properties!['category']) .properties!['category'])
: const Text(""), : const Text(""),
trailing: Column( trailing: Column(
crossAxisAlignment: CrossAxisAlignment.end, crossAxisAlignment: CrossAxisAlignment.end,
children: [ children: [
indexController.locations[0].collection[index] indexController.locations[0].features[index]!
.properties!['sub_loc_id'] != .properties!['sub_loc_id'] !=
null null
? Text(indexController ? Text(indexController.locations[0]
.locations[0] .features[index]!.properties!['sub_loc_id'])
.collection[index]
.properties!['sub_loc_id'])
: const Text(""), : const Text(""),
SizedBox( SizedBox(
width: 100, width: 100,

View File

@ -1,42 +1,48 @@
import 'dart:async'; import 'dart:async';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_map/plugin_api.dart'; import 'package:flutter_map/flutter_map.dart';
import 'package:flutter_map_location_marker/flutter_map_location_marker.dart'; import 'package:flutter_map_location_marker/flutter_map_location_marker.dart';
import 'package:flutter_map_marker_cluster/flutter_map_marker_cluster.dart'; import 'package:flutter_map_marker_cluster/flutter_map_marker_cluster.dart';
import 'package:flutter_polyline_points/flutter_polyline_points.dart'; import 'package:flutter_polyline_points/flutter_polyline_points.dart';
import 'package:geojson/geojson.dart'; import 'package:geojson_vi/geojson_vi.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:latlong2/latlong.dart'; import 'package:latlong2/latlong.dart';
import 'package:rogapp/model/destination.dart'; import 'package:rogapp/model/destination.dart';
import 'package:rogapp/pages/destination/destination_controller.dart'; import 'package:rogapp/pages/destination/destination_controller.dart';
import 'package:rogapp/pages/index/index_controller.dart'; import 'package:rogapp/pages/index/index_controller.dart';
import 'package:rogapp/utils/database_helper.dart'; import 'package:rogapp/utils/database_helper.dart';
import 'package:rogapp/utils/location_controller.dart';
import 'package:rogapp/utils/text_util.dart'; import 'package:rogapp/utils/text_util.dart';
import 'package:rogapp/widgets/base_layer_widget.dart'; import 'package:rogapp/widgets/base_layer_widget.dart';
import 'package:rogapp/widgets/bottom_sheet_new.dart'; import 'package:rogapp/widgets/bottom_sheet_new.dart';
import 'package:rogapp/widgets/debug_widget.dart'; import 'package:rogapp/widgets/current_position_widget.dart';
import 'package:rogapp/widgets/game_state_view.dart';
class MapWidget extends StatelessWidget {
final IndexController indexController = Get.find<IndexController>();
final DestinationController destinationController =
Get.find<DestinationController>();
class MapWidget extends StatefulWidget {
MapWidget({Key? key}) : super(key: key); MapWidget({Key? key}) : super(key: key);
StreamSubscription? subscription; @override
State<MapWidget> createState() => _MapWidgetState();
}
Widget getMarkerShape(GeoJsonFeature i, BuildContext context) { class _MapWidgetState extends State<MapWidget> {
GeoJsonMultiPoint p = i.geometry as GeoJsonMultiPoint; final IndexController indexController = Get.find<IndexController>();
final DestinationController destinationController =
Get.find<DestinationController>();
final LocationController locationController = Get.find<LocationController>();
StreamSubscription? subscription;
Timer? _timer;
Widget getMarkerShape(GeoJSONFeature i, BuildContext context) {
GeoJSONMultiPoint p = i.geometry as GeoJSONMultiPoint;
//print("lat is ${p.geoSerie!.geoPoints[0].latitude} and lon is ${p.geoSerie!.geoPoints[0].longitude}"); //print("lat is ${p.geoSerie!.geoPoints[0].latitude} and lon is ${p.geoSerie!.geoPoints[0].longitude}");
//RegExp regex = RegExp(r'([.]*0)(?!.*\d)'); //RegExp regex = RegExp(r'([.]*0)(?!.*\d)');
return Row( return InkWell(
mainAxisAlignment: MainAxisAlignment.start,
children: [
InkWell(
onTap: () { onTap: () {
GeoJsonFeature? fs = indexController.getFeatureForLatLong( GeoJSONFeature? fs = indexController.getFeatureForLatLong(
p.geoSerie!.geoPoints[0].latitude, p.coordinates[0][1], p.coordinates[0][0]);
p.geoSerie!.geoPoints[0].longitude);
//print("------- fs $fs------"); //print("------- fs $fs------");
if (fs != null) { if (fs != null) {
indexController.currentFeature.clear(); indexController.currentFeature.clear();
@ -47,9 +53,10 @@ class MapWidget extends StatelessWidget {
DatabaseHelper db = DatabaseHelper.instance; DatabaseHelper db = DatabaseHelper.instance;
db.getDestinationByLatLon(des.lat!, des.lon!).then((value) { db.getDestinationByLatLon(des.lat!, des.lon!).then((value) {
destinationController.shouldShowBottomSheet = false;
showModalBottomSheet( showModalBottomSheet(
constraints: BoxConstraints.loose( constraints:
Size(Get.width, Get.height * 0.85)), BoxConstraints.loose(Size(Get.width, Get.height * 0.85)),
context: context, context: context,
isScrollControlled: true, isScrollControlled: true,
isDismissible: true, isDismissible: true,
@ -57,12 +64,17 @@ class MapWidget extends StatelessWidget {
destination: des, isAlreadyCheckedIn: value.isNotEmpty)) destination: des, isAlreadyCheckedIn: value.isNotEmpty))
//builder:((context) => BottomSheetWidget()) //builder:((context) => BottomSheetWidget())
).whenComplete(() { ).whenComplete(() {
destinationController.shouldShowBottomSheet = true;
destinationController.skipGps = false; destinationController.skipGps = false;
}); });
}); });
} }
}, },
child: Container( child: Stack(
fit: StackFit.expand,
//mainAxisAlignment: MainAxisAlignment.center,
children: [
Container(
height: 32, height: 32,
width: 32, width: 32,
decoration: BoxDecoration( decoration: BoxDecoration(
@ -82,7 +94,9 @@ class MapWidget extends StatelessWidget {
size: 6.0, size: 6.0,
), ),
i.properties!['cp'] == -1 i.properties!['cp'] == -1
? Transform.rotate( ? Transform.translate(
offset: Offset(18, 0),
child: Transform.rotate(
alignment: Alignment.centerLeft, alignment: Alignment.centerLeft,
origin: Offset.fromDirection(1, 26), origin: Offset.fromDirection(1, 26),
angle: 270 * pi / 180, angle: 270 * pi / 180,
@ -90,34 +104,54 @@ class MapWidget extends StatelessWidget {
Icons.play_arrow_outlined, Icons.play_arrow_outlined,
color: Colors.red, color: Colors.red,
size: 70, size: 70,
)) )),
)
: Container( : Container(
color: Colors.transparent, color: Colors.transparent,
), ),
], ],
)), )),
), Transform.translate(
Container( offset: Offset(45, 0),
color: Colors.purple.withOpacity(0.4), child: Align(
alignment: Alignment.center,
child: Container(
color: Colors.purple.withOpacity(0.2),
// child: Text(TextUtils.getDisplayTextFeture(i), // child: Text(TextUtils.getDisplayTextFeture(i),
// style: const TextStyle( // style: const TextStyle(
// fontSize: 16, // fontSize: 16,
// fontWeight: FontWeight.bold, // fontWeight: FontWeight.bold,
// color: Colors.red, // color: Colors.red,
// ))), // ))),
child: Text( child: Stack(
children: <Widget>[
// Text with white outline
Text(
TextUtils.getDisplayTextFeture(i), TextUtils.getDisplayTextFeture(i),
style: TextStyle( style: TextStyle(
fontSize: 16, fontSize: 16,
fontWeight: FontWeight.w700, fontWeight: FontWeight.w700,
// アウトラインの色と幅を設定
foreground: Paint() foreground: Paint()
..style = PaintingStyle.stroke ..style = PaintingStyle.stroke
..strokeWidth = 1 ..strokeWidth = 1
..color = Colors.white, ..color = Colors.white,
), ),
)) ),
// Text with black fill
Text(
TextUtils.getDisplayTextFeture(i),
style: TextStyle(
fontSize: 16,
fontWeight: FontWeight.w700,
color: Colors.black,
),
),
], ],
)),
),
)
],
),
); );
} }
@ -131,6 +165,33 @@ class MapWidget extends StatelessWidget {
return pts; return pts;
} }
@override
void initState() {
super.initState();
_startIdleTimer();
}
void _startIdleTimer() {
_timer = Timer(const Duration(milliseconds: (1000 * 10)), _centerMapOnUser);
}
void _resetTimer() {
_timer?.cancel();
_startIdleTimer();
}
void _centerMapOnUser() {
assert(() {
print("showBottomSheet ${destinationController.shouldShowBottomSheet}");
return true;
}());
// 2024-04-03 Akira Log enabled only debug mode..
//
//if (destinationController.shouldShowBottomSheet) {
destinationController.centerMapToCurrentLocation();
//}
}
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
// print( // print(
@ -152,7 +213,8 @@ class MapWidget extends StatelessWidget {
subscription = indexController.mapController.mapEventStream subscription = indexController.mapController.mapEventStream
.listen((MapEvent mapEvent) { .listen((MapEvent mapEvent) {
if (mapEvent is MapEventMoveStart) { if (mapEvent is MapEventMoveStart) {
//print(DateTime.now().toString() + ' [MapEventMoveStart] START'); // print(DateTime.now().toString() +
// ' [MapEventMoveStart] START');
// do something // do something
} }
if (mapEvent is MapEventMoveEnd) {} if (mapEvent is MapEventMoveEnd) {}
@ -169,7 +231,11 @@ class MapWidget extends StatelessWidget {
interactiveFlags: interactiveFlags:
InteractiveFlag.pinchZoom | InteractiveFlag.drag, InteractiveFlag.pinchZoom | InteractiveFlag.drag,
onPositionChanged: (MapPosition pos, isvalue) { onPositionChanged: (MapPosition pos, hasGesture) {
//print("map position changed ${pos.center!.latitude}");
if (hasGesture) {
_resetTimer();
}
indexController.currentBound = [pos.bounds!]; indexController.currentBound = [pos.bounds!];
}, },
onTap: (_, __) => popupController onTap: (_, __) => popupController
@ -190,7 +256,9 @@ class MapWidget extends StatelessWidget {
: Container(), : Container(),
), ),
CurrentLocationLayer( CurrentLocationLayer(
followOnLocationUpdate: FollowOnLocationUpdate.never, positionStream: locationController
.locationMarkerPositionStreamController.stream,
alignDirectionOnUpdate: AlignOnUpdate.never,
turnOnHeadingUpdate: TurnOnHeadingUpdate.never, turnOnHeadingUpdate: TurnOnHeadingUpdate.never,
style: const LocationMarkerStyle( style: const LocationMarkerStyle(
marker: DefaultLocationMarker( marker: DefaultLocationMarker(
@ -204,37 +272,36 @@ class MapWidget extends StatelessWidget {
), ),
), ),
indexController.locations.isNotEmpty && indexController.locations.isNotEmpty &&
indexController.locations[0].collection.isNotEmpty indexController.locations[0].features.isNotEmpty
? MarkerLayer( ? MarkerLayer(
markers: markers:
indexController.locations[0].collection.map((i) { indexController.locations[0].features.map((i) {
//print("i si ${i.properties!['location_id']}"); //print("i si ${i.properties!['location_id']}");
RegExp regex = RegExp(r'([.]*0)(?!.*\d)'); RegExp regex = RegExp(r'([.]*0)(?!.*\d)');
GeoJsonMultiPoint p = GeoJSONMultiPoint p =
i.geometry as GeoJsonMultiPoint; i!.geometry as GeoJSONMultiPoint;
//print( //print(
// "lat is ${p.geoSerie!.geoPoints[0].latitude} and lon is ${p.geoSerie!.geoPoints[0].longitude}"); // "lat is ${p.geoSerie!.geoPoints[0].latitude} and lon is ${p.geoSerie!.geoPoints[0].longitude}");
return Marker( return Marker(
anchorPos: AnchorPos.exactly(Anchor(108.0, 18.0)), alignment: Alignment.center,
height: 32.0, height: 27.0,
width: 120.0, width: 127.0,
point: LatLng(p.geoSerie!.geoPoints[0].latitude, point: LatLng(
p.geoSerie!.geoPoints[0].longitude), p.coordinates[0][1], p.coordinates[0][0]),
builder: (ctx) { child: getMarkerShape(i, context));
return getMarkerShape(i, context);
},
);
}).toList(), }).toList(),
) )
: const Center(child: CircularProgressIndicator()), : const Center(child: CircularProgressIndicator()),
], ],
)), )),
const Positioned( const Positioned(top: 0, left: 0, child: GameStateWidget()),
bottom: 10, const Positioned(bottom: 10, right: 10, child: CurrentPosition())
left: 0, // const Positioned(
child: DebugWidget(), // bottom: 10,
) // left: 0,
// child: DebugWidget(),
// )
], ],
); );
} }

View File

@ -5,9 +5,9 @@ PODS:
- file_selector_macos (0.0.1): - file_selector_macos (0.0.1):
- FlutterMacOS - FlutterMacOS
- FlutterMacOS (1.0.0) - FlutterMacOS (1.0.0)
- FMDB (2.7.5): - FMDB (2.7.10):
- FMDB/standard (= 2.7.5) - FMDB/standard (= 2.7.10)
- FMDB/standard (2.7.5) - FMDB/standard (2.7.10)
- geolocator_apple (1.2.0): - geolocator_apple (1.2.0):
- FlutterMacOS - FlutterMacOS
- isar_flutter_libs (1.0.0): - isar_flutter_libs (1.0.0):
@ -15,7 +15,7 @@ PODS:
- path_provider_foundation (0.0.1): - path_provider_foundation (0.0.1):
- Flutter - Flutter
- FlutterMacOS - FlutterMacOS
- ReachabilitySwift (5.0.0) - ReachabilitySwift (5.2.1)
- shared_preferences_foundation (0.0.1): - shared_preferences_foundation (0.0.1):
- Flutter - Flutter
- FlutterMacOS - FlutterMacOS
@ -65,15 +65,15 @@ SPEC CHECKSUMS:
connectivity_plus: 18d3c32514c886e046de60e9c13895109866c747 connectivity_plus: 18d3c32514c886e046de60e9c13895109866c747
file_selector_macos: 468fb6b81fac7c0e88d71317f3eec34c3b008ff9 file_selector_macos: 468fb6b81fac7c0e88d71317f3eec34c3b008ff9
FlutterMacOS: 8f6f14fa908a6fb3fba0cd85dbd81ec4b251fb24 FlutterMacOS: 8f6f14fa908a6fb3fba0cd85dbd81ec4b251fb24
FMDB: 2ce00b547f966261cd18927a3ddb07cb6f3db82a FMDB: eae540775bf7d0c87a5af926ae37af69effe5a19
geolocator_apple: 72a78ae3f3e4ec0db62117bd93e34523f5011d58 geolocator_apple: 72a78ae3f3e4ec0db62117bd93e34523f5011d58
isar_flutter_libs: 43385c99864c168fadba7c9adeddc5d38838ca6a isar_flutter_libs: 43385c99864c168fadba7c9adeddc5d38838ca6a
path_provider_foundation: 29f094ae23ebbca9d3d0cec13889cd9060c0e943 path_provider_foundation: 3784922295ac71e43754bd15e0653ccfd36a147c
ReachabilitySwift: 985039c6f7b23a1da463388634119492ff86c825 ReachabilitySwift: 5ae15e16814b5f9ef568963fb2c87aeb49158c66
shared_preferences_foundation: 5b919d13b803cadd15ed2dc053125c68730e5126 shared_preferences_foundation: b4c3b4cddf1c21f02770737f147a3f5da9d39695
sqflite: a5789cceda41d54d23f31d6de539d65bb14100ea sqflite: d0307f984e859ce2bd39b230d672a448ea3f47b4
url_launcher_macos: d2691c7dd33ed713bf3544850a623080ec693d95 url_launcher_macos: d2691c7dd33ed713bf3544850a623080ec693d95
PODFILE CHECKSUM: 236401fc2c932af29a9fcf0e97baeeb2d750d367 PODFILE CHECKSUM: 236401fc2c932af29a9fcf0e97baeeb2d750d367
COCOAPODS: 1.12.1 COCOAPODS: 1.15.2

View File

@ -195,7 +195,6 @@
DB3AD6E65B5CC8A5A9E2767E /* Pods-RunnerTests.release.xcconfig */, DB3AD6E65B5CC8A5A9E2767E /* Pods-RunnerTests.release.xcconfig */,
6114E0F2A0E1D978BBC23F48 /* Pods-RunnerTests.profile.xcconfig */, 6114E0F2A0E1D978BBC23F48 /* Pods-RunnerTests.profile.xcconfig */,
); );
name = Pods;
path = Pods; path = Pods;
sourceTree = "<group>"; sourceTree = "<group>";
}; };
@ -259,7 +258,7 @@
isa = PBXProject; isa = PBXProject;
attributes = { attributes = {
LastSwiftUpdateCheck = 0920; LastSwiftUpdateCheck = 0920;
LastUpgradeCheck = 1430; LastUpgradeCheck = 1510;
ORGANIZATIONNAME = ""; ORGANIZATIONNAME = "";
TargetAttributes = { TargetAttributes = {
331C80D4294CF70F00263BE5 = { 331C80D4294CF70F00263BE5 = {
@ -342,6 +341,7 @@
}; };
33CC111E2044C6BF0003C045 /* ShellScript */ = { 33CC111E2044C6BF0003C045 /* ShellScript */ = {
isa = PBXShellScriptBuildPhase; isa = PBXShellScriptBuildPhase;
alwaysOutOfDate = 1;
buildActionMask = 2147483647; buildActionMask = 2147483647;
files = ( files = (
); );
@ -358,7 +358,7 @@
); );
runOnlyForDeploymentPostprocessing = 0; runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh; shellPath = /bin/sh;
shellScript = "\"$FLUTTER_ROOT\"/packages/flutter_tools/bin/macos_assemble.sh && touch Flutter/ephemeral/tripwire"; shellScript = "\"$FLUTTER_ROOT\"/packages/flutter_tools/bin/macos_assemble.sh && touch Flutter/ephemeral/tripwire\n";
}; };
427A05FAB0ED774C4EAAB828 /* [CP] Check Pods Manifest.lock */ = { 427A05FAB0ED774C4EAAB828 /* [CP] Check Pods Manifest.lock */ = {
isa = PBXShellScriptBuildPhase; isa = PBXShellScriptBuildPhase;

View File

@ -1,6 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<Scheme <Scheme
LastUpgradeVersion = "1430" LastUpgradeVersion = "1510"
version = "1.3"> version = "1.3">
<BuildAction <BuildAction
parallelizeBuildables = "YES" parallelizeBuildables = "YES"

File diff suppressed because it is too large Load Diff

View File

@ -15,7 +15,7 @@ publish_to: "none" # Remove this line if you wish to publish to pub.dev
# In iOS, build-name is used as CFBundleShortVersionString while build-number used as CFBundleVersion. # In iOS, build-name is used as CFBundleShortVersionString while build-number used as CFBundleVersion.
# Read more about iOS versioning at # Read more about iOS versioning at
# https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html # https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html
version: 1.0.26+26 version: 1.0.33+33
environment: environment:
sdk: ">=3.1.0 <4.0.0" sdk: ">=3.1.0 <4.0.0"
@ -35,12 +35,17 @@ dependencies:
cupertino_icons: ^1.0.2 cupertino_icons: ^1.0.2
sqflite: ^2.0.1 sqflite: ^2.0.1
get: ^4.6.6 get: ^4.6.6
flutter_map: ^4.0.0 flutter_map: ^6.0.1
geolocator: ^9.0.2 geolocator: ^10.1.0
permission_handler: ^10.0.0 permission_handler: ^11.3.1
# permission_handler: ^11.1.0 <== older
# permission_handler 11.2.0 (11.3.1 available)
# permission_handler_android 12.0.3 (12.0.5 available)
# permission_handler_apple 9.3.0 (9.4.4 available)
# permission_handler_platform_interface 4.1.0 (4.2.1 available)
google_api_availability: ^5.0.0 google_api_availability: ^5.0.0
tuple: ^2.0.0 tuple: ^2.0.0
latlong2: ^0.8.1 latlong2: ^0.9.0
positioned_tap_detector_2: ^1.0.4 positioned_tap_detector_2: ^1.0.4
transparent_image: ^2.0.0 transparent_image: ^2.0.0
async: ^2.8.2 async: ^2.8.2
@ -53,31 +58,32 @@ dependencies:
flutter_map_location_marker: any flutter_map_location_marker: any
flutter_map_marker_cluster: any flutter_map_marker_cluster: any
material_design_icons_flutter: ^7.0.7296 material_design_icons_flutter: ^7.0.7296
google_fonts: ^4.0.4 google_fonts: ^6.1.0
keyboard_dismisser: ^3.0.0 keyboard_dismisser: ^3.0.0
image_picker: ^1.0.4 image_picker: ^1.0.4
#geojson_vi: ^2.0.7 geojson_vi: ^2.2.1
geojson: ^1.0.0 #geojson: ^1.0.0
url_launcher: ^6.0.20 url_launcher: ^6.0.20
flutter_breadcrumb: ^1.0.1 flutter_breadcrumb: ^1.0.1
timeline_tile: ^2.0.0 timeline_tile: ^2.0.0
# google_maps_flutter: ^2.5.0 # google_maps_flutter: ^2.5.0
#flutter_map_marker_popup: any #flutter_map_marker_popup: any
flutter_polyline_points: ^1.0.0 flutter_polyline_points: ^2.0.0
google_maps_webservice: ^0.0.19 #google_maps_webservice: ^0.0.20-nullsafety.5
flutter_typeahead: ^4.0.0 flutter_typeahead: ^5.0.1
flutter_launcher_icons: ^0.13.1 flutter_launcher_icons: ^0.13.1
rename: ^2.0.1 rename: ^3.0.1
circular_menu: ^2.0.1 circular_menu: ^2.0.1
camera_camera: ^3.0.0 camera_camera: ^3.0.0
intl: ^0.18.1 intl: ^0.18.1
modal_bottom_sheet: ^3.0.0-pre modal_bottom_sheet: ^3.0.0-pre
connectivity_plus: ^4.0.2 connectivity_plus: ^5.0.2
flutter_map_tile_caching: ^8.0.1 flutter_map_tile_caching: ^9.0.0-dev.5
shared_preferences: ^2.0.15 shared_preferences: ^2.0.15
gallery_saver: ^2.3.2 # gallery_saver: ^2.3.2
image_gallery_saver: ^2.0.3
flutter_riverpod: ^2.4.0 flutter_riverpod: ^2.4.0
http: ^0.13.6 http: ^1.1.0
flutter_icons: flutter_icons:
android: true android: true
@ -93,7 +99,7 @@ dev_dependencies:
# activated in the `analysis_options.yaml` file located at the root of your # activated in the `analysis_options.yaml` file located at the root of your
# package. See that file for information about deactivating specific lint # package. See that file for information about deactivating specific lint
# rules and activating additional ones. # rules and activating additional ones.
flutter_lints: ^2.0.3 flutter_lints: ^3.0.1
# For information on the generic Dart part of this file, see the # For information on the generic Dart part of this file, see the
# following page: https://dart.dev/tools/pub/pubspec # following page: https://dart.dev/tools/pub/pubspec