import 'package:flutter/material.dart'; import '../../../core/network/api_client.dart'; import '../../../core/theme/app_theme.dart'; class InAppAdminModal { static void show(BuildContext context) { showModalBottomSheet( context: context, isScrollControlled: true, backgroundColor: Colors.transparent, builder: (modalCtx) => const _AdminSheetContent(), ); } } class _AdminSheetContent extends StatefulWidget { const _AdminSheetContent(); @override State<_AdminSheetContent> createState() => _AdminSheetContentState(); } class _AdminSheetContentState extends State<_AdminSheetContent> with SingleTickerProviderStateMixin { late TabController _tabController; final _client = ApiClient(); // Add Partner Form Controllers final _nameController = TextEditingController(); final _cityController = TextEditingController(text: 'بغداد'); final _countryController = TextEditingController(text: 'العراق'); final _discountController = TextEditingController(text: '50'); final _phoneController = TextEditingController(); final _addressController = TextEditingController(); String _partnerType = 'HOSPITAL'; bool _isAdding = false; @override void initState() { super.initState(); _tabController = TabController(length: 2, vsync: this); } @override void dispose() { _tabController.dispose(); _nameController.dispose(); _cityController.dispose(); _countryController.dispose(); _discountController.dispose(); _phoneController.dispose(); _addressController.dispose(); super.dispose(); } Future _submitNewPartner() async { final name = _nameController.text.trim(); if (name.isEmpty) { ScaffoldMessenger.of(context).showSnackBar(const SnackBar(content: Text('يرجى كتابة اسم المستشفى أو الفندق.'))); return; } setState(() => _isAdding = true); try { await _client.post('/api/v1/admin/partners/add', body: { 'name_ar': name, 'type': _partnerType, 'city': _cityController.text.trim(), 'country': _countryController.text.trim(), 'discount_percentage': double.tryParse(_discountController.text.trim()) ?? 50.0, 'phone': _phoneController.text.trim(), 'address': _addressController.text.trim(), }); if (mounted) { Navigator.of(context).pop(); ScaffoldMessenger.of(context).showSnackBar( const SnackBar( content: Text('تمت إضافة الشريك بنجاح ومتاح فورياً لجميع المشتركين!'), backgroundColor: AppTheme.emeraldGreen, ), ); } } catch (e) { if (mounted) { ScaffoldMessenger.of(context).showSnackBar(SnackBar(content: Text('حدث خطأ: $e'), backgroundColor: AppTheme.crimsonRed)); } } finally { if (mounted) setState(() => _isAdding = false); } } @override Widget build(BuildContext context) { return Directionality( textDirection: TextDirection.rtl, child: Container( height: MediaQuery.of(context).size.height * 0.85, padding: const EdgeInsets.all(20), decoration: const BoxDecoration( color: AppTheme.primaryDark, borderRadius: BorderRadius.vertical(top: Radius.circular(24)), ), child: Column( children: [ Container(width: 40, height: 4, decoration: BoxDecoration(color: Colors.white24, borderRadius: BorderRadius.circular(2))), const SizedBox(height: 16), const Row( mainAxisAlignment: MainAxisAlignment.center, children: [ Icon(Icons.admin_panel_settings, color: AppTheme.goldAccent, size: 24), SizedBox(width: 8), Text( 'لوحة إدارة جائزة أوروك (خاص بالإدارة)', style: TextStyle(color: AppTheme.goldLight, fontSize: 17, fontWeight: FontWeight.bold), ), ], ), const SizedBox(height: 14), TabBar( controller: _tabController, indicatorColor: AppTheme.goldAccent, labelColor: AppTheme.goldLight, unselectedLabelColor: AppTheme.textMuted, tabs: const [ Tab(text: 'إضافة مستشفى / فندق'), Tab(text: 'الحوالات المعلقة'), ], ), const SizedBox(height: 14), Expanded( child: TabBarView( controller: _tabController, children: [ // Tab 1: Add Partner Form _buildAddPartnerTab(), // Tab 2: Pending Payments _buildPendingPaymentsTab(), ], ), ), ], ), ), ); } Widget _buildAddPartnerTab() { return SingleChildScrollView( child: Column( crossAxisAlignment: CrossAxisAlignment.stretch, children: [ Row( children: [ Expanded( child: RadioListTile( title: const Text('مستشفى (50%)', style: TextStyle(color: Colors.white, fontSize: 13)), value: 'HOSPITAL', groupValue: _partnerType, activeColor: AppTheme.goldAccent, onChanged: (v) => setState(() { _partnerType = v!; _discountController.text = '50'; }), ), ), Expanded( child: RadioListTile( title: const Text('فندق (سياحي)', style: TextStyle(color: Colors.white, fontSize: 13)), value: 'HOTEL', groupValue: _partnerType, activeColor: AppTheme.goldAccent, onChanged: (v) => setState(() { _partnerType = v!; _discountController.text = '45'; }), ), ), ], ), const SizedBox(height: 8), _buildTextField(_nameController, 'اسم الشريك (مثال: مستشفى الشرق الأوسط / فندق بابل)', Icons.business), const SizedBox(height: 12), Row( children: [ Expanded(child: _buildTextField(_cityController, 'المدينة (بغداد، أربيل، عمان..)', Icons.location_city)), const SizedBox(width: 8), Expanded(child: _buildTextField(_countryController, 'الدولة', Icons.public)), ], ), const SizedBox(height: 12), Row( children: [ Expanded(child: _buildTextField(_discountController, 'نسبة الخصم %', Icons.percent, isNumber: true)), const SizedBox(width: 8), Expanded(child: _buildTextField(_phoneController, 'رقم الهاتف', Icons.phone)), ], ), const SizedBox(height: 12), _buildTextField(_addressController, 'العنوان التفصيلي', Icons.map), const SizedBox(height: 20), SizedBox( height: 50, child: ElevatedButton( onPressed: _isAdding ? null : _submitNewPartner, child: _isAdding ? const CircularProgressIndicator(color: AppTheme.primaryDark) : const Text('حفظ ونشر الشريك فورياً لجميع المشتركين'), ), ), ], ), ); } Widget _buildPendingPaymentsTab() { return FutureBuilder>( future: _client.get('/api/v1/admin/payments/pending'), builder: (context, snapshot) { if (snapshot.connectionState == ConnectionState.waiting) { return const Center(child: CircularProgressIndicator(color: AppTheme.goldAccent)); } if (snapshot.hasError) { return Center(child: Text('خطأ: ${snapshot.error}', style: const TextStyle(color: AppTheme.textMuted))); } final list = (snapshot.data?['data'] as List?) ?? []; if (list.isEmpty) { return const Center( child: Text('لا توجد حوالات معلقة حالياً.', style: TextStyle(color: AppTheme.textMuted)), ); } return ListView.builder( itemCount: list.length, itemBuilder: (ctx, i) { final item = list[i] as Map; return Card( color: AppTheme.cardDark, margin: const EdgeInsets.only(bottom: 10), child: ListTile( title: Text(item['full_name'] ?? 'مشترك جديد', style: const TextStyle(color: Colors.white)), subtitle: Text( '${item['method']} • رقم الحركة: ${item['reference_number']}', style: const TextStyle(color: AppTheme.textMuted, fontSize: 12), ), trailing: ElevatedButton( style: ElevatedButton.styleFrom( backgroundColor: AppTheme.emeraldGreen, padding: const EdgeInsets.symmetric(horizontal: 12, vertical: 8), ), onPressed: () async { await _client.post('/api/v1/admin/payments/approve', body: {'transaction_id': item['id']}); setState(() {}); }, child: const Text('تفعيل', style: TextStyle(fontSize: 12)), ), ), ); }, ); }, ); } Widget _buildTextField(TextEditingController controller, String label, IconData icon, {bool isNumber = false}) { return TextField( controller: controller, keyboardType: isNumber ? TextInputType.number : TextInputType.text, style: const TextStyle(color: Colors.white, fontSize: 14), decoration: InputDecoration( labelText: label, labelStyle: const TextStyle(color: AppTheme.textMuted, fontSize: 13), prefixIcon: Icon(icon, color: AppTheme.goldAccent, size: 20), filled: true, fillColor: AppTheme.cardDark, border: OutlineInputBorder(borderRadius: BorderRadius.circular(12), borderSide: BorderSide.none), contentPadding: const EdgeInsets.symmetric(horizontal: 14, vertical: 12), ), ); } }