diff --git a/lib/screens/menu_browse_screen.dart b/lib/screens/menu_browse_screen.dart index f05e5a9..9a060f8 100644 --- a/lib/screens/menu_browse_screen.dart +++ b/lib/screens/menu_browse_screen.dart @@ -1046,63 +1046,127 @@ class _ItemCustomizationSheetState extends State<_ItemCustomizationSheet> { builder: (context, scrollController) { return Column( children: [ - // Header + // Header with item image Container( - padding: const EdgeInsets.all(20), decoration: BoxDecoration( - color: Theme.of(context).colorScheme.surface, - border: Border( - bottom: BorderSide( - color: Theme.of(context).colorScheme.outlineVariant, - width: 1, + color: Colors.white, + boxShadow: [ + BoxShadow( + color: Colors.black.withOpacity(0.05), + blurRadius: 10, + offset: const Offset(0, 2), ), - ), + ], ), child: Column( - crossAxisAlignment: CrossAxisAlignment.start, children: [ - Row( - children: [ - Container( - width: 12, - height: 4, - margin: const EdgeInsets.only(right: 8), - decoration: BoxDecoration( - color: Theme.of(context).colorScheme.onSurfaceVariant, - borderRadius: BorderRadius.circular(2), - ), + // Drag handle + Center( + child: Container( + width: 40, + height: 4, + margin: const EdgeInsets.only(top: 12), + decoration: BoxDecoration( + color: Colors.grey.shade300, + borderRadius: BorderRadius.circular(2), ), - ], + ), ), - const SizedBox(height: 16), - Text( - widget.item.name, - style: Theme.of(context).textTheme.headlineSmall?.copyWith( - fontWeight: FontWeight.bold, + Padding( + padding: const EdgeInsets.all(20), + child: Row( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + // Item image + Container( + width: 100, + height: 100, + decoration: BoxDecoration( + borderRadius: BorderRadius.circular(16), + boxShadow: [ + BoxShadow( + color: Colors.black.withOpacity(0.1), + blurRadius: 8, + offset: const Offset(0, 4), + ), + ], + ), + child: ClipRRect( + borderRadius: BorderRadius.circular(16), + child: Image.network( + "https://biz.payfrit.com/uploads/items/${widget.item.itemId}.png", + fit: BoxFit.cover, + errorBuilder: (context, error, stackTrace) { + return Image.network( + "https://biz.payfrit.com/uploads/items/${widget.item.itemId}.jpg", + fit: BoxFit.cover, + errorBuilder: (context, error, stackTrace) { + return Container( + decoration: BoxDecoration( + gradient: LinearGradient( + begin: Alignment.topLeft, + end: Alignment.bottomRight, + colors: [Colors.blue.shade100, Colors.blue.shade200], + ), + ), + child: Center( + child: Icon( + Icons.restaurant_menu, + color: Colors.blue.shade400, + size: 40, + ), + ), + ); + }, + ); + }, + ), + ), ), - ), - if (widget.item.description.isNotEmpty) ...[ - const SizedBox(height: 8), - Text( - widget.item.description, - style: Theme.of(context).textTheme.bodyMedium?.copyWith( - color: Theme.of(context).colorScheme.onSurfaceVariant, - ), - ), - ], - const SizedBox(height: 12), - Container( - padding: const EdgeInsets.symmetric(horizontal: 16, vertical: 8), - decoration: BoxDecoration( - color: Theme.of(context).colorScheme.primaryContainer, - borderRadius: BorderRadius.circular(20), - ), - child: Text( - "Base: \$${widget.item.price.toStringAsFixed(2)}", - style: Theme.of(context).textTheme.labelLarge?.copyWith( - color: Theme.of(context).colorScheme.onPrimaryContainer, - fontWeight: FontWeight.w600, + const SizedBox(width: 16), + // Item details + Expanded( + child: Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + Text( + widget.item.name, + style: Theme.of(context).textTheme.titleLarge?.copyWith( + fontWeight: FontWeight.bold, + ), + ), + if (widget.item.description.isNotEmpty) ...[ + const SizedBox(height: 8), + Text( + widget.item.description, + style: Theme.of(context).textTheme.bodyMedium?.copyWith( + color: Colors.grey.shade600, + ), + maxLines: 2, + overflow: TextOverflow.ellipsis, + ), + ], + const SizedBox(height: 12), + Container( + padding: const EdgeInsets.symmetric(horizontal: 14, vertical: 6), + decoration: BoxDecoration( + color: Colors.green.shade50, + borderRadius: BorderRadius.circular(20), + border: Border.all(color: Colors.green.shade200), + ), + child: Text( + "\$${widget.item.price.toStringAsFixed(2)}", + style: TextStyle( + color: Colors.green.shade700, + fontWeight: FontWeight.bold, + fontSize: 16, + ), + ), + ), + ], ), + ), + ], ), ), ], @@ -1120,14 +1184,14 @@ class _ItemCustomizationSheetState extends State<_ItemCustomizationSheet> { // Footer with validation error and add button Container( - padding: const EdgeInsets.all(16), + padding: const EdgeInsets.fromLTRB(20, 16, 20, 20), decoration: BoxDecoration( - color: Theme.of(context).colorScheme.surface, + color: Colors.white, boxShadow: [ BoxShadow( - color: Colors.black.withAlpha(25), - blurRadius: 4, - offset: const Offset(0, -2), + color: Colors.black.withOpacity(0.1), + blurRadius: 10, + offset: const Offset(0, -4), ), ], ), @@ -1141,17 +1205,20 @@ class _ItemCustomizationSheetState extends State<_ItemCustomizationSheet> { margin: const EdgeInsets.only(bottom: 12), decoration: BoxDecoration( color: Colors.red.shade50, - borderRadius: BorderRadius.circular(8), - border: Border.all(color: Colors.red.shade300), + borderRadius: BorderRadius.circular(12), + border: Border.all(color: Colors.red.shade200), ), child: Row( children: [ - Icon(Icons.error_outline, color: Colors.red.shade700), - const SizedBox(width: 12), + Icon(Icons.error_outline, color: Colors.red.shade600, size: 20), + const SizedBox(width: 10), Expanded( child: Text( _validationError!, - style: TextStyle(color: Colors.red.shade900), + style: TextStyle( + color: Colors.red.shade800, + fontSize: 13, + ), ), ), ], @@ -1160,9 +1227,47 @@ class _ItemCustomizationSheetState extends State<_ItemCustomizationSheet> { ], SizedBox( width: double.infinity, - child: FilledButton( + height: 56, + child: ElevatedButton( onPressed: _handleAdd, - child: Text("Add to Cart - \$${_calculateTotal().toStringAsFixed(2)}"), + style: ElevatedButton.styleFrom( + backgroundColor: Colors.blue.shade600, + foregroundColor: Colors.white, + elevation: 2, + shadowColor: Colors.blue.shade200, + shape: RoundedRectangleBorder( + borderRadius: BorderRadius.circular(16), + ), + ), + child: Row( + mainAxisAlignment: MainAxisAlignment.center, + children: [ + const Icon(Icons.add_shopping_cart, size: 22), + const SizedBox(width: 10), + Text( + "Add to Cart", + style: const TextStyle( + fontSize: 16, + fontWeight: FontWeight.w600, + ), + ), + const SizedBox(width: 8), + Container( + padding: const EdgeInsets.symmetric(horizontal: 10, vertical: 4), + decoration: BoxDecoration( + color: Colors.white.withOpacity(0.2), + borderRadius: BorderRadius.circular(12), + ), + child: Text( + "\$${_calculateTotal().toStringAsFixed(2)}", + style: const TextStyle( + fontSize: 15, + fontWeight: FontWeight.bold, + ), + ), + ), + ], + ), ), ), ], @@ -1223,15 +1328,58 @@ class _ItemCustomizationSheetState extends State<_ItemCustomizationSheet> { } Widget _buildSelectableItem(MenuItem item, MenuItem parent, int depth) { + final isSelected = _selectedItemIds.contains(item.itemId); + return Padding( - padding: EdgeInsets.only(left: depth * 16.0), - child: ListTile( - leading: _buildSelectionWidget(item, parent), - title: Text(item.name), - subtitle: item.price > 0 - ? Text("+\$${item.price.toStringAsFixed(2)}") - : null, - onTap: () => _toggleSelection(item, parent), + padding: EdgeInsets.only(left: depth * 16.0, bottom: 8), + child: Material( + color: isSelected ? Colors.blue.shade50 : Colors.grey.shade50, + borderRadius: BorderRadius.circular(12), + child: InkWell( + borderRadius: BorderRadius.circular(12), + onTap: () => _toggleSelection(item, parent), + child: Container( + padding: const EdgeInsets.symmetric(horizontal: 12, vertical: 10), + decoration: BoxDecoration( + borderRadius: BorderRadius.circular(12), + border: Border.all( + color: isSelected ? Colors.blue.shade300 : Colors.grey.shade200, + width: isSelected ? 2 : 1, + ), + ), + child: Row( + children: [ + _buildSelectionWidget(item, parent), + const SizedBox(width: 12), + Expanded( + child: Text( + item.name, + style: TextStyle( + fontWeight: isSelected ? FontWeight.w600 : FontWeight.normal, + color: isSelected ? Colors.blue.shade800 : Colors.black87, + ), + ), + ), + if (item.price > 0) + Container( + padding: const EdgeInsets.symmetric(horizontal: 8, vertical: 4), + decoration: BoxDecoration( + color: Colors.green.shade50, + borderRadius: BorderRadius.circular(8), + ), + child: Text( + "+\$${item.price.toStringAsFixed(2)}", + style: TextStyle( + color: Colors.green.shade700, + fontWeight: FontWeight.w600, + fontSize: 13, + ), + ), + ), + ], + ), + ), + ), ), ); }