// lib/screens/restaurant_select_screen.dart import "package:flutter/material.dart"; import "package:provider/provider.dart"; import "../app/app_router.dart"; import "../app/app_state.dart"; import "../models/restaurant.dart"; import "../models/service_point.dart"; import "../services/api.dart"; class RestaurantSelectScreen extends StatefulWidget { const RestaurantSelectScreen({super.key}); @override State createState() => _RestaurantSelectScreenState(); } class _RestaurantSelectScreenState extends State { late Future> _future; String? _debugLastRaw; int? _debugLastStatus; @override void initState() { super.initState(); _future = _load(); } Future> _load() async { final raw = await Api.listRestaurantsRaw(); _debugLastRaw = raw.rawBody; _debugLastStatus = raw.statusCode; return Api.listRestaurants(); } Future _selectBusinessAndContinue(Restaurant r) async { final appState = context.read(); // You MUST have a userId for ordering. final userId = appState.userId; if (userId == null || userId <= 0) { if (!mounted) return; ScaffoldMessenger.of(context).showSnackBar( const SnackBar(content: Text("Missing UserID (not logged in).")), ); return; } // Set selected business appState.setBusiness(r.businessId); // Go pick service point, and WAIT for a selection. final sp = await Navigator.of(context).pushNamed( AppRoutes.servicePointSelect, arguments: { "BusinessID": r.businessId, "UserID": userId, }, ); if (!mounted) return; if (sp is ServicePoint) { // Store selection in AppState appState.setServicePoint(sp.servicePointId); // Navigate to Menu Browse Navigator.of(context).pushNamed( AppRoutes.menuBrowse, arguments: { "BusinessID": r.businessId, "ServicePointID": sp.servicePointId, "UserID": userId, }, ); } } @override Widget build(BuildContext context) { return Scaffold( appBar: AppBar( title: const Text("Select Business"), ), body: FutureBuilder>( future: _future, builder: (context, snapshot) { if (snapshot.connectionState == ConnectionState.waiting) { return const Center(child: CircularProgressIndicator()); } if (snapshot.hasError) { return _ErrorPane( title: "Businesses Load Failed", message: snapshot.error.toString(), statusCode: _debugLastStatus, raw: _debugLastRaw, onRetry: () => setState(() => _future = _load()), ); } final items = snapshot.data ?? const []; if (items.isEmpty) { return _ErrorPane( title: "No Businesses Returned", message: "The API returned an empty list.", statusCode: _debugLastStatus, raw: _debugLastRaw, onRetry: () => setState(() => _future = _load()), ); } return ListView.builder( padding: const EdgeInsets.all(16), itemCount: items.length, itemBuilder: (context, i) { final r = items[i]; return Container( margin: const EdgeInsets.only(bottom: 12), decoration: BoxDecoration( borderRadius: BorderRadius.circular(16), boxShadow: [ BoxShadow( color: Colors.black.withAlpha(15), blurRadius: 8, offset: const Offset(0, 2), ), ], ), child: Material( borderRadius: BorderRadius.circular(16), color: Theme.of(context).colorScheme.surface, child: InkWell( borderRadius: BorderRadius.circular(16), onTap: () => _selectBusinessAndContinue(r), child: Padding( padding: const EdgeInsets.all(20), child: Row( children: [ Container( width: 56, height: 56, decoration: BoxDecoration( color: Theme.of(context).colorScheme.primaryContainer, borderRadius: BorderRadius.circular(12), ), child: Icon( Icons.store, size: 32, color: Theme.of(context).colorScheme.onPrimaryContainer, ), ), const SizedBox(width: 16), Expanded( child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ Text( r.name, style: Theme.of(context).textTheme.titleLarge?.copyWith( fontWeight: FontWeight.w600, ), ), const SizedBox(height: 4), Text( "Tap to view menu", style: Theme.of(context).textTheme.bodyMedium?.copyWith( color: Theme.of(context).colorScheme.onSurfaceVariant, ), ), ], ), ), Icon( Icons.arrow_forward_ios, color: Theme.of(context).colorScheme.onSurfaceVariant, size: 20, ), ], ), ), ), ), ); }, ); }, ), ); } } class _ErrorPane extends StatelessWidget { final String title; final String message; final int? statusCode; final String? raw; final VoidCallback onRetry; const _ErrorPane({ required this.title, required this.message, required this.statusCode, required this.raw, required this.onRetry, }); @override Widget build(BuildContext context) { return Center( child: SingleChildScrollView( padding: const EdgeInsets.all(18), child: ConstrainedBox( constraints: const BoxConstraints(maxWidth: 720), child: Card( child: Padding( padding: const EdgeInsets.all(18), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ Text(title, style: Theme.of(context).textTheme.titleLarge), const SizedBox(height: 10), Text(message), const SizedBox(height: 14), if (statusCode != null) Text("HTTP: $statusCode"), if (raw != null && raw!.trim().isNotEmpty) ...[ const SizedBox(height: 10), const Text("Raw response:"), const SizedBox(height: 6), Text(raw!), ], const SizedBox(height: 14), FilledButton( onPressed: onRetry, child: const Text("Retry"), ), ], ), ), ), ), ), ); } }