Merge branch 'favorites'
This commit is contained in:
		
						commit
						707ad2e9c4
					
				| @ -1,3 +1,5 @@ | ||||
| import 'dart:math'; | ||||
| 
 | ||||
| import 'package:flutter/material.dart'; | ||||
| import 'package:shared_preferences/shared_preferences.dart'; | ||||
| import 'package:http/http.dart' as http; | ||||
| @ -69,7 +71,7 @@ Future<bool> isLoggedIn(BuildContext context) async { | ||||
| 
 | ||||
|   try { | ||||
|     String base64 = token.split('.')[1]; | ||||
|     base64 += List.filled(4 - base64.length % 4, '=').join(); | ||||
|     base64 += List.filled(base64.length % 4 == 0 ? 0 : 4 - base64.length % 4, '=').join(); | ||||
| 
 | ||||
|     final payload = jsonDecode(String.fromCharCodes(base64Decode(base64))); | ||||
| 
 | ||||
| @ -81,6 +83,7 @@ Future<bool> isLoggedIn(BuildContext context) async { | ||||
|   } catch (e) { | ||||
|     messenger.showSnackBar(const SnackBar(content: Text('Invalid token, please sign in again'))); | ||||
|     prefs.remove('token'); | ||||
|     debugPrint(e.toString()); | ||||
|     return false; | ||||
|   } | ||||
| 
 | ||||
|  | ||||
| @ -83,14 +83,14 @@ class _SideMenuState extends State<SideMenu> { | ||||
|               }, | ||||
|             ), | ||||
|             ListTile( | ||||
|               title: const Text('Favourites'), | ||||
|               title: const Text('Favorites'), | ||||
|               leading: const Icon(Icons.star), | ||||
|               selected: _selectedIndex == 1, | ||||
|               onTap: () { | ||||
|                 // Update the state of the app | ||||
|                 _onItemTapped(1); | ||||
|                 // Then close the drawer | ||||
|                 Navigator.pushReplacementNamed(context, '/favourites'); | ||||
|                 Navigator.pushReplacementNamed(context, '/favorites'); | ||||
|               }, | ||||
|             ), | ||||
|             ListTile( | ||||
|  | ||||
							
								
								
									
										61
									
								
								Mobile/lib/favorites.dart
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										61
									
								
								Mobile/lib/favorites.dart
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,61 @@ | ||||
| import 'dart:convert'; | ||||
| import 'api.dart' as api; | ||||
| import 'package:flutter/material.dart'; | ||||
| import 'base/sidemenu.dart'; // Import the base layout widget | ||||
| import 'models.dart'; | ||||
| 
 | ||||
| class FavoritesPage extends StatefulWidget { | ||||
|   const FavoritesPage({super.key}); | ||||
| 
 | ||||
|   @override | ||||
|   State<FavoritesPage> createState() => _FavoritesPage(); | ||||
| } | ||||
| 
 | ||||
| class _FavoritesPage extends State<FavoritesPage> { | ||||
|   List<Favorite> _favorites = []; | ||||
| 
 | ||||
|   @override | ||||
|   void didChangeDependencies() { | ||||
|     super.didChangeDependencies(); | ||||
| 
 | ||||
|     api.isLoggedIn(context).then((isLoggedIn) async { | ||||
|       if (!isLoggedIn || !mounted) return; | ||||
| 
 | ||||
|       final response = await api.request(context, api.ApiService.app, 'GET', '/favorites', null); | ||||
|       if (response == null) return; | ||||
| 
 | ||||
|       final List<dynamic> favorites = jsonDecode(response); | ||||
|       setState(() { | ||||
|         _favorites = favorites.map((favorite) => Favorite(favorite['id'], favorite['user_id'], favorite['lat'], favorite['lng'])).toList(); | ||||
|       }); | ||||
|     }); | ||||
| 
 | ||||
|   } | ||||
|   @override | ||||
|   Widget build(BuildContext context) { | ||||
|     return SideMenu( | ||||
|       body: Container( | ||||
|         decoration: BoxDecoration(color: Color(0xFFF9F9F9)), | ||||
|         width: MediaQuery.of(context).size.width, | ||||
|         padding: const EdgeInsets.all(20.0), | ||||
|         child: Column(children: | ||||
|           _favorites.map((favorite) => Container( | ||||
|             width: double.infinity, | ||||
|             padding: const EdgeInsets.all(20.0), | ||||
|             decoration: const BoxDecoration( | ||||
|               boxShadow: [ | ||||
|                 BoxShadow( | ||||
|                   color: Color(0x20000000), | ||||
|                   offset: Offset(0, 1), | ||||
|                   blurRadius: 4, | ||||
|                 ), | ||||
|               ], | ||||
|               color: Colors.white | ||||
|             ), | ||||
|             child: const Text("Favorite data here"), | ||||
|           )).toList(), | ||||
|         ), | ||||
|       ), | ||||
|     ); | ||||
|   } | ||||
| } | ||||
| @ -1,15 +0,0 @@ | ||||
| import 'package:flutter/material.dart'; | ||||
| import 'base/sidemenu.dart'; // Import the base layout widget | ||||
| 
 | ||||
| class FavouritesPage extends StatelessWidget { | ||||
|   const FavouritesPage({super.key}); | ||||
| 
 | ||||
|   @override | ||||
|   Widget build(BuildContext context) { | ||||
|     return const SideMenu( | ||||
|       body: Center( | ||||
|         child: Text('This is Page 1'), | ||||
|       ), | ||||
|     ); | ||||
|   } | ||||
| } | ||||
| @ -1,11 +1,16 @@ | ||||
| import 'dart:convert'; | ||||
| import 'dart:developer'; | ||||
| 
 | ||||
| import 'package:flutter/material.dart'; | ||||
| import 'package:flutter_map/flutter_map.dart'; | ||||
| import 'package:latlong2/latlong.dart'; | ||||
| import 'package:mobile/favourites.dart'; | ||||
| import 'package:mobile/favorites.dart'; | ||||
| import 'package:mobile/register.dart'; | ||||
| import 'login.dart'; | ||||
| import 'base/sidemenu.dart'; | ||||
| import 'profile.dart'; | ||||
| import 'api.dart' as api; | ||||
| import 'models.dart'; | ||||
| 
 | ||||
| void main() { | ||||
|   runApp(const MyApp()); | ||||
| @ -26,7 +31,7 @@ class MyApp extends StatelessWidget { | ||||
|       routes: { | ||||
|         '/home': (context) => const MyHomePage(), | ||||
|         '/profile': (context) => const ProfilePage(), | ||||
|         '/favourites': (context) => const FavouritesPage(), | ||||
|         '/favorites': (context) => const FavoritesPage(), | ||||
|         '/login': (context) => const LoginPage(), | ||||
|         '/register': (context) => const RegisterPage(), | ||||
|       }, | ||||
| @ -43,6 +48,26 @@ class MyHomePage extends StatefulWidget { | ||||
| 
 | ||||
| class _MyHomePageState extends State<MyHomePage> { | ||||
|   final GlobalKey<ScaffoldState> _scaffoldKey = GlobalKey<ScaffoldState>(); | ||||
|   List<Favorite> _favorites = []; | ||||
| 
 | ||||
|   @override | ||||
|   void didChangeDependencies() { | ||||
|     super.didChangeDependencies(); | ||||
| 
 | ||||
|     api.isLoggedIn(context).then((isLoggedIn) async { | ||||
|       if (!isLoggedIn || !mounted) return; | ||||
| 
 | ||||
|       final response = await api.request(context, api.ApiService.app, 'GET', '/favorites', null); | ||||
|       if (response == null) return; | ||||
| 
 | ||||
|       final List<dynamic> favorites = jsonDecode(response); | ||||
|       setState(() { | ||||
|         _favorites = favorites.map((favorite) => Favorite(favorite['id'], favorite['user_id'], favorite['lat'], favorite['lng'])).toList(); | ||||
|       }); | ||||
|     }); | ||||
| 
 | ||||
|   } | ||||
| 
 | ||||
|   @override | ||||
|   Widget build(BuildContext context) { | ||||
|     return SideMenu( | ||||
| @ -50,23 +75,24 @@ class _MyHomePageState extends State<MyHomePage> { | ||||
|         key: _scaffoldKey, | ||||
|         //drawer: navigationMenu, | ||||
|         body: FlutterMap( | ||||
|           options: const MapOptions( | ||||
|               initialCenter: LatLng(55.9397, 9.5156), initialZoom: 7.0), | ||||
|           options: const MapOptions(initialCenter: LatLng(55.9397, 9.5156), initialZoom: 7.0), | ||||
|           children: [ | ||||
|             openStreetMapTileLayer, | ||||
|             const MarkerLayer(markers: [ | ||||
|               Marker( | ||||
|                 point: LatLng(56.465511, 9.411366), | ||||
|                 width: 60, | ||||
|                 height: 100, | ||||
|                 alignment: Alignment.center, | ||||
|                 child: Icon( | ||||
|                   Icons.location_pin, | ||||
|                   size: 60, | ||||
|                   color: Colors.purple, | ||||
|                 ), | ||||
|               ), | ||||
|             ]), | ||||
|             ..._favorites.map((favorite) => | ||||
|               MarkerLayer(markers: [ | ||||
|                 Marker( | ||||
|                   point: LatLng(favorite.lat, favorite.lng), | ||||
|                   width: 60, | ||||
|                   height: 100, | ||||
|                   alignment: Alignment.center, | ||||
|                   child: const Icon( | ||||
|                     Icons.location_pin, | ||||
|                     size: 60, | ||||
|                     color: Colors.yellow, | ||||
|                   ) | ||||
|                 ) | ||||
|               ]) | ||||
|             ), | ||||
|           ], | ||||
|         ), | ||||
|       ), | ||||
|  | ||||
							
								
								
									
										8
									
								
								Mobile/lib/models.dart
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										8
									
								
								Mobile/lib/models.dart
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,8 @@ | ||||
| class Favorite { | ||||
|   int id; | ||||
|   String userId; | ||||
|   double lat; | ||||
|   double lng; | ||||
| 
 | ||||
|   Favorite(this.id, this.userId, this.lat, this.lng); | ||||
| } | ||||
| @ -17,10 +17,10 @@ class _RegisterPageState extends State<RegisterPage> { | ||||
| 
 | ||||
|   Future<void> _register() async { | ||||
|     if (passwordInput.text != confirmPasswordInput.text) { | ||||
|       ScaffoldMessenger.of(context).showSnackBar(const SnackBar(content: Text('Passwords do not match'))); | ||||
|       ScaffoldMessenger.of(context).showSnackBar( | ||||
|           const SnackBar(content: Text('Passwords do not match'))); | ||||
|       return; | ||||
|     } | ||||
| 
 | ||||
|     final result = await api.request(context, api.ApiService.auth, 'POST', '/api/Users', { | ||||
|       'username': usernameInput.text, | ||||
|       'email': emailInput.text, | ||||
|  | ||||
		Loading…
	
		Reference in New Issue
	
	Block a user