import os file_path = "/Users/maddy/Projects/Kifi/kifi-app/lib/features/inventory/presentation/product_detail_screen.dart" content = """import 'package:flutter/material.dart'; import 'package:flutter_riverpod/flutter_riverpod.dart'; import 'package:kifi_app/features/inventory/providers/products_provider.dart'; import 'package:kifi_app/core/network/dio_client.dart'; import 'package:kifi_app/features/inventory/domain/product.dart'; import 'package:kifi_app/features/inventory/presentation/add_product_screen.dart'; import 'package:kifi_app/features/inventory/presentation/stock_ledger_tab.dart'; import 'package:kifi_app/features/inventory/presentation/widgets/adjust_stock_sheet.dart'; class ProductDetailScreen extends ConsumerWidget { final Product product; const ProductDetailScreen({super.key, required this.product}); @override Widget build(BuildContext context, WidgetRef ref) { // Watch products to get latest updates (like stock changes) final productsState = ref.watch(productsProvider); final currentProduct = productsState.value?.firstWhere((p) => p.id == product.id, orElse: () => product) ?? product; return DefaultTabController( length: 2, child: Scaffold( backgroundColor: Colors.grey[50], appBar: AppBar( elevation: 0, backgroundColor: Colors.white, foregroundColor: Colors.black, title: Text(currentProduct.name, style: const TextStyle(fontWeight: FontWeight.bold)), actions: [ IconButton( icon: const Icon(Icons.edit, color: Colors.black), onPressed: () { Navigator.push( context, MaterialPageRoute( builder: (context) => AddProductScreen(product: currentProduct), ), ); }, ), ], bottom: const TabBar( labelColor: Colors.blue, unselectedLabelColor: Colors.grey, indicatorColor: Colors.blue, tabs: [ Tab(text: "Overview"), Tab(text: "Stock Ledger"), ], ), ), body: TabBarView( children: [ _buildOverviewTab(context, currentProduct, ref), StockLedgerTab(productId: currentProduct.id!), ], ), floatingActionButton: FloatingActionButton.extended( onPressed: () { showModalBottomSheet( context: context, isScrollControlled: true, backgroundColor: Colors.transparent, builder: (context) => AdjustStockSheet(productId: currentProduct.id!), ); }, backgroundColor: Colors.blue, icon: const Icon(Icons.inventory), label: const Text("Adjust Stock"), ), ), ); } Widget _buildOverviewTab(BuildContext context, Product p, WidgetRef ref) { return SingleChildScrollView( padding: const EdgeInsets.all(16.0), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ // Image Header if (p.imageIds.isNotEmpty) Container( height: 200, width: double.infinity, decoration: BoxDecoration( borderRadius: BorderRadius.circular(12), color: Colors.grey[200], ), clipBehavior: Clip.antiAlias, child: FutureBuilder( future: DioClient().storage.read(key: 'jwt_token'), builder: (context, snapshot) { if (snapshot.connectionState == ConnectionState.waiting) { return const Center(child: CircularProgressIndicator()); } final token = snapshot.data; if (token == null) { return const Icon(Icons.image, size: 50, color: Colors.grey); } return Image.network( '${DioClient().dio.options.baseUrl}/inventory/products/${p.id}/images/${p.imageIds.first}/content', fit: BoxFit.cover, headers: {'Authorization': 'Bearer $token'}, errorBuilder: (context, error, stackTrace) => const Icon(Icons.image, size: 50, color: Colors.grey), ); }, ), ), const SizedBox(height: 24), // Stock Summary Card Card( elevation: 0, shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(12)), child: Padding( padding: const EdgeInsets.all(16.0), child: Row( children: [ Container( padding: const EdgeInsets.all(12), decoration: BoxDecoration( color: Colors.blue.withOpacity(0.1), shape: BoxShape.circle, ), child: const Icon(Icons.inventory_2, color: Colors.blue), ), const SizedBox(width: 16), Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ Text("Current Stock", style: TextStyle(color: Colors.grey[600], fontSize: 14)), Text( "${p.currentStock ?? 0}", style: const TextStyle(fontWeight: FontWeight.bold, fontSize: 24), ), ], ), ], ), ), ), const SizedBox(height: 16), // Details Card Card( elevation: 0, shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(12)), child: Padding( padding: const EdgeInsets.all(16.0), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ const Text("Metal Details", style: TextStyle(fontWeight: FontWeight.bold, fontSize: 16)), const Divider(), _buildDetailRow("SKU / HUID", p.sku ?? "-"), _buildDetailRow("Gross Weight", "${p.weight ?? 0} g"), _buildDetailRow("Purity Factor", "${p.purityFactor ?? 1.0}"), _buildDetailRow("Wastage", "${p.wastagePercentage ?? 0}%"), _buildDetailRow("Net Weight", "${(p.weight ?? 0) * (1 - (p.wastagePercentage ?? 0) / 100)} g"), ], ), ), ), const SizedBox(height: 16), // Pricing Card Card( elevation: 0, shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(12)), child: Padding( padding: const EdgeInsets.all(16.0), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ const Text("Pricing Details", style: TextStyle(fontWeight: FontWeight.bold, fontSize: 16)), const Divider(), _buildDetailRow("Making Charges", "₹${p.makingCharges?.toStringAsFixed(2) ?? '0.00'} (${p.makingChargesType})"), _buildDetailRow("HSN Code", p.hsnCode ?? "-"), _buildDetailRow("GST Rate", "${p.gstRate?.toStringAsFixed(1) ?? '0'}%"), ], ), ), ), ], ), ); } Widget _buildDetailRow(String label, String value) { return Padding( padding: const EdgeInsets.symmetric(vertical: 8.0), child: Row( mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ Text(label, style: TextStyle(color: Colors.grey[600])), Text(value, style: const TextStyle(fontWeight: FontWeight.w500)), ], ), ); } } """ with open(file_path, "w") as f: f.write(content)