import 'dart:async';
import 'dart:convert';
import 'dart:io';
import 'dart:ui'; // للألوان

import 'package:flutter/material.dart';
import 'package:flutter_local_notifications/flutter_local_notifications.dart';
import 'package:get/get.dart';
import 'package:permission_handler/permission_handler.dart';
import 'package:timezone/data/latest.dart' as tz;
import 'package:timezone/timezone.dart' as tz;

import '../../constant/box_name.dart';
import '../../constant/links.dart';
import '../../main.dart'; // للوصول لـ box
import '../../print.dart';
import '../../views/home/Captin/driver_map_page.dart';
import '../../views/home/Captin/orderCaptin/order_request_page.dart';
import '../functions/crud.dart';
import '../home/captin/home_captain_controller.dart';

class NotificationController extends GetxController {
  final FlutterLocalNotificationsPlugin _flutterLocalNotificationsPlugin =
      FlutterLocalNotificationsPlugin();

  // ==============================================================================
  // 1. تهيئة الإشعارات (إعداد القنوات والأزرار للآيفون والأندرويد)
  // ==============================================================================
  Future<void> initNotifications() async {
    // إعدادات الأندرويد
    const AndroidInitializationSettings android =
        AndroidInitializationSettings('@mipmap/launcher_icon');

    // إعدادات أزرار الآيفون (Categories)
    // هذا الجزء ضروري لظهور الأزرار في iOS
    final List<DarwinNotificationCategory> darwinNotificationCategories = [
      DarwinNotificationCategory(
        'ORDER_CATEGORY', // المعرف المستخدم لربط الإشعار بالأزرار
        actions: [
          DarwinNotificationAction.plain('ACCEPT_ORDER', '✅ قبول'),
          DarwinNotificationAction.plain('SHOW_DETAILS', '📄 تفاصيل'),
          DarwinNotificationAction.plain(
            'REJECT_ORDER',
            '❌ رفض',
            options: {
              DarwinNotificationActionOption.destructive
            }, // يظهر باللون الأحمر
          ),
        ],
      )
    ];

    // إعدادات الآيفون العامة
    final DarwinInitializationSettings ios = DarwinInitializationSettings(
      requestAlertPermission: true,
      requestBadgePermission: true,
      requestSoundPermission: true,
      notificationCategories: darwinNotificationCategories, // تسجيل الأزرار
    );

    InitializationSettings initializationSettings =
        InitializationSettings(android: android, iOS: ios);

    tz.initializeTimeZones();
    print('✅ Notifications initialized with Action Buttons Support');

    await _flutterLocalNotificationsPlugin.initialize(
      onDidReceiveNotificationResponse: onDidReceiveNotificationResponse,
      onDidReceiveBackgroundNotificationResponse: notificationTapBackground,
      settings: initializationSettings,
    );

    // إنشاء قناة الأندرويد ذات الأهمية القصوى
    const AndroidNotificationChannel channel = AndroidNotificationChannel(
      'high_importance_channel',
      'High Importance Notifications',
      description: 'This channel is used for important notifications.',
      importance: Importance.max, // أقصى أهمية
      playSound: true,
    );

    await _flutterLocalNotificationsPlugin
        .resolvePlatformSpecificImplementation<
            AndroidFlutterLocalNotificationsPlugin>()
        ?.createNotificationChannel(channel);
  }

  // ==============================================================================
  // 2. دالة عرض الإشعار المطور (شكل واضح + أزرار + صوت مخصص)
  // ==============================================================================
  void showOrderNotification(
      String title, String body, String tone, String myListString) async {
    // أ) تنسيق النص والبيانات بشكل جميل
    String formattedBigText = body;
    String summaryText = 'طلب جديد';
    String price = '';

    try {
      List<dynamic> data = jsonDecode(myListString);
      // استخراج البيانات (تأكد أن الاندكسات مطابقة للباك إند عندك)
      price = _getVal(data, 26);
      String distance = _getVal(data, 5);
      String startLoc = _getVal(data, 29);
      String endLoc = _getVal(data, 30);
      String paxName = _getVal(data, 8);
      // String rating = _getVal(data, 33);

      // تنسيق النص ليكون 4 أسطر واضحة
      formattedBigText = "👤 $paxName\n"
          "💰 $price ${'SYP'.tr}   |   🛣️ $distance كم\n"
          "🟢 من: $startLoc\n"
          "🏁 إلى: $endLoc";

      summaryText = 'سعر الرحلة: $price';
    } catch (e) {
      print("Error formatting notification text: $e");
    }

    // ب) نمط النص الكبير (BigText) للأندرويد
    BigTextStyleInformation bigTextStyleInformation = BigTextStyleInformation(
      formattedBigText,
      contentTitle: '🚖 $title',
      summaryText: summaryText,
      htmlFormatContent: true,
      htmlFormatContentTitle: true,
    );

    // ج) معالجة اسم الصوت (أندرويد بدون امتداد، آيفون مع امتداد)
    String soundNameAndroid = tone.contains('.') ? tone.split('.').first : tone;
    String soundNameIOS = tone.contains('.') ? tone : "$tone.wav";

    // د) إعدادات الأندرويد (الأزرار + Full Screen)
    final androidDetails = AndroidNotificationDetails(
      'high_importance_channel',
      'High Importance Notifications',
      importance: Importance.max,
      priority: Priority.max,
      fullScreenIntent: true, // يفتح الشاشة وتظهر التفاصيل
      category: AndroidNotificationCategory.call, // يعامل كمكالمة (رنين مستمر)
      visibility: NotificationVisibility.public,
      ongoing: true, // يمنع الحذف بالسحب
      sound: RawResourceAndroidNotificationSound(soundNameAndroid),
      audioAttributesUsage: AudioAttributesUsage.alarm, // صوت عالٍ كالمنبه
      styleInformation: bigTextStyleInformation,
      color: const Color(0xFF1A252F),

      // الأزرار الثلاثة
      actions: <AndroidNotificationAction>[
        const AndroidNotificationAction(
          'ACCEPT_ORDER',
          '✅ قبول فوري',
          showsUserInterface: true,
          titleColor: Color(0xFF4CAF50), // أخضر
        ),
        const AndroidNotificationAction(
          'SHOW_DETAILS',
          '📄 التفاصيل',
          showsUserInterface: true,
          titleColor: Color(0xFF2196F3), // أزرق
        ),
        const AndroidNotificationAction(
          'REJECT_ORDER',
          '❌ رفض',
          showsUserInterface: false, // لا يفتح التطبيق
          cancelNotification: true,
          titleColor: Color(0xFFE53935), // أحمر
        ),
      ],
    );

    // هـ) إعدادات الآيفون
    final iosDetails = DarwinNotificationDetails(
      sound: soundNameIOS,
      presentAlert: true,
      presentBadge: true,
      presentSound: true,
      categoryIdentifier: 'ORDER_CATEGORY', // ربط الأزرار
      interruptionLevel: InterruptionLevel.critical, // محاولة لكسر الصامت
    );

    final details =
        NotificationDetails(android: androidDetails, iOS: iosDetails);

    // عرض الإشعار
    await _flutterLocalNotificationsPlugin.show(
      id: 1001, // ID ثابت لاستبدال الإشعار القديم
      title: title,
      body: "$price - مسافة $formattedBigText", // نص مختصر يظهر في البار العلوي
      notificationDetails: details,
      payload: jsonEncode({
        'type': 'Order',
        'data': myListString,
      }),
    );
  }

  // ==============================================================================
  // 3. معالجة الاستجابة (عند الضغط على الأزرار)
  // ==============================================================================
  Future<void> handleNotificationResponse(NotificationResponse response) async {
    final payload = response.payload;
    if (payload == null) return;

    final payloadData = jsonDecode(payload) as Map<String, dynamic>;
    final rawData = payloadData['data'];

    List<dynamic> listData = [];
    if (rawData is String) {
      listData = jsonDecode(rawData);
    } else if (rawData is List) {
      listData = rawData;
    }

    print("🔔 Notification Action: ${response.actionId}");

    // أ) زر القبول
    if (response.actionId == 'ACCEPT_ORDER') {
      await _flutterLocalNotificationsPlugin.cancel(id: 1001); // حذف الإشعار
      _processAcceptOrder(listData);
    }

    // ب) زر التفاصيل
    else if (response.actionId == 'SHOW_DETAILS') {
      // await _flutterLocalNotificationsPlugin.cancel(1001); // اختياري: حذف الإشعار
      Get.to(() => OrderRequestPage(), arguments: {'myListString': rawData});
    }

    // ج) زر الرفض
    else if (response.actionId == 'REJECT_ORDER') {
      await _flutterLocalNotificationsPlugin.cancel(id: 1001); // حذف الإشعار
      _processRejectOrder(listData);
    }

    // د) الضغط على الإشعار نفسه (بدون أزرار)
    else {
      Get.to(() => OrderRequestPage(), arguments: {'myListString': rawData});
    }
  }

  // ==============================================================================
  // 4. منطق القبول الآمن (Safe Accept Logic)
  // ==============================================================================
  Future<void> _processAcceptOrder(List<dynamic> data) async {
    // إظهار Loading
    Get.dialog(
      WillPopScope(
        onWillPop: () async => false,
        child: const Center(
          child: CircularProgressIndicator(color: Colors.white),
        ),
      ),
      barrierDismissible: false,
    );

    try {
      final driverId = box.read(BoxName.driverID);
      String orderId = _getVal(data, 16);
      String passengerToken = _getVal(data, 9);

      print("🚀 Sending Accept Request for Order: $orderId");

      var res = await CRUD().post(
        link: "${AppLink.ride}/rides/acceptRide.php",
        payload: {
          'id': orderId,
          'rideTimeStart': DateTime.now().toString(),
          'status': 'Apply',
          'passengerToken': passengerToken,
          'driver_id': driverId,
        },
      );

      print("📥 Server Response: $res");

      if (Get.isDialogOpen == true) Get.back(); // إغلاق اللودينج

      // 🔴 فحص النتيجة بدقة (Map أو String)
      bool isFailure = false;
      if (res is Map && res['status'] == 'failure') {
        isFailure = true;
      } else if (res == 'failure') {
        isFailure = true;
      }

      if (isFailure) {
        Get.defaultDialog(
          title: "تنبيه",
          middleText: "عذراً، الطلب أخذه سائق آخر.",
          confirmTextColor: Colors.white,
          onConfirm: () => Get.back(),
          textConfirm: "حسناً",
        );
        return; // توقف هنا ولا تكمل
      }

      // ✅ نجاح -> تجهيز الانتقال

      // حماية من الكراش: التأكد من وجود HomeCaptainController
      if (!Get.isRegistered<HomeCaptainController>()) {
        print("♻️ Reviving HomeCaptainController...");
        Get.put(HomeCaptainController());
      } else {
        Get.find<HomeCaptainController>().changeRideId();
      }

      box.write(BoxName.statusDriverLocation, 'on');
      box.write(BoxName.rideStatus, 'Apply');

      var rideArgs = _buildRideArgs(data);
      box.write(BoxName.rideArguments, rideArgs);

      // استخدام offAll لمنع الرجوع لصفحة الطلب
      Get.offAll(() => PassengerLocationMapPage(), arguments: rideArgs);
    } catch (e) {
      if (Get.isDialogOpen == true) Get.back();
      print("❌ Error in accept process: $e");
      Get.snackbar("خطأ", "حدث خطأ غير متوقع");
    }
  }

  // ==============================================================================
  // 5. منطق الرفض (يعمل في الخلفية بدون فتح صفحات)
  // ==============================================================================
  Future<void> _processRejectOrder(List<dynamic> data) async {
    try {
      final driverId = box.read(BoxName.driverID);
      String orderId = _getVal(data, 16);

      if (driverId != null && orderId.isNotEmpty) {
        print("📤 Rejecting Order: $orderId");
        await CRUD().post(link: AppLink.addDriverOrder, payload: {
          'driver_id': driverId,
          'order_id': orderId,
          'status': 'Refused'
        });
        print("✅ Order Rejected Successfully");
      }
    } catch (e) {
      print("❌ Error rejecting order: $e");
    }
  }

  // ==============================================================================
  // 6. دوال مساعدة (Helpers)
  // ==============================================================================

  Map<String, dynamic> _buildRideArgs(List<dynamic> data) {
    return {
      'passengerLocation': '${_getVal(data, 0)},${_getVal(data, 1)}',
      'passengerDestination': '${_getVal(data, 3)},${_getVal(data, 4)}',
      'Duration': _getVal(data, 4), // انتبه: تأكد من الإندكس الصحيح للوقت
      'totalCost': _getVal(data, 26),
      'Distance': _getVal(data, 5),
      'name': _getVal(data, 8),
      'phone': _getVal(data, 10),
      'email': _getVal(data, 28),
      'WalletChecked': _getVal(data, 13),
      'tokenPassenger': _getVal(data, 9),
      'direction':
          'https://www.google.com/maps/dir/${_getVal(data, 0)}/${_getVal(data, 1)}/',
      'DurationToPassenger': _getVal(data, 15),
      'rideId': _getVal(data, 16),
      'passengerId': _getVal(data, 7),
      'driverId': _getVal(data, 18),
      'durationOfRideValue': _getVal(data, 19),
      'paymentAmount': _getVal(data, 2),
      'paymentMethod': _getVal(data, 13) == 'true' ? 'visa' : 'cash',
      'isHaveSteps': _getVal(data, 20),
      'step0': _getVal(data, 21),
      'step1': _getVal(data, 22),
      'step2': _getVal(data, 23),
      'step3': _getVal(data, 24),
      'step4': _getVal(data, 25),
      'passengerWalletBurc': _getVal(data, 26),
      'timeOfOrder': DateTime.now().toString(),
      'totalPassenger': _getVal(data, 2),
      'carType': _getVal(data, 31),
      'kazan': _getVal(data, 32),
      'startNameLocation': _getVal(data, 29),
      'endNameLocation': _getVal(data, 30),
    };
  }

  String _getVal(List<dynamic> data, int index) {
    if (data.length > index && data[index] != null) {
      return data[index].toString();
    }
    return '';
  }

  // Callbacks
  void onDidReceiveNotificationResponse(NotificationResponse response) {
    handleNotificationResponse(response);
  }

  void onDidReceiveBackgroundNotificationResponse(
      NotificationResponse response) {
    handleNotificationResponse(response);
  }

  // ==============================================================================
  // 7. الدوال القديمة (Old Scheduled Notifications) - لم يتم تغييرها
  // ==============================================================================

  void showNotification(
      String title, String message, String tone, String payLoad) async {
    // هذه الدالة القديمة للإشعارات البسيطة (ليس الطلبات)
    BigTextStyleInformation bigTextStyleInformation = BigTextStyleInformation(
      message,
      contentTitle: title.tr,
      htmlFormatContent: true,
      htmlFormatContentTitle: true,
    );
    AndroidNotificationDetails android = AndroidNotificationDetails(
      'high_importance_channel',
      'High Importance Notifications',
      importance: Importance.max,
      priority: Priority.high,
      sound: RawResourceAndroidNotificationSound(tone.split('.').first),
    );

    DarwinNotificationDetails ios = const DarwinNotificationDetails(
      sound: 'default',
      presentAlert: true,
      presentBadge: true,
      presentSound: true,
    );
    NotificationDetails details =
        NotificationDetails(android: android, iOS: ios);

    await _flutterLocalNotificationsPlugin.show(
        id: 0,
        title: title,
        body: message,
        notificationDetails: details,
        payload: jsonEncode({'title': title, 'data': payLoad}));
  }

  void scheduleNotificationsForSevenDays(
      String title, String message, String tone) async {
    final AndroidNotificationDetails android = AndroidNotificationDetails(
      'high_importance_channel',
      'High Importance Notifications',
      importance: Importance.max,
      priority: Priority.high,
      sound: RawResourceAndroidNotificationSound(tone.split('.').first),
    );

    const DarwinNotificationDetails ios = DarwinNotificationDetails(
      sound: 'default',
      presentAlert: true,
      presentBadge: true,
      presentSound: true,
    );

    final NotificationDetails details =
        NotificationDetails(android: android, iOS: ios);

    if (Platform.isAndroid) {
      if (await Permission.scheduleExactAlarm.isDenied) {
        await Permission.scheduleExactAlarm.request();
      }
    }

    for (int day = 0; day < 7; day++) {
      final notificationTimes = [
        {'hour': 8, 'minute': 0, 'id': day * 1000 + 1},
        {'hour': 15, 'minute': 0, 'id': day * 1000 + 2},
        {'hour': 20, 'minute': 0, 'id': day * 1000 + 3},
      ];

      for (var time in notificationTimes) {
        final notificationId = time['id'] as int;
        bool isScheduled = box.read('notification_$notificationId') ?? false;

        if (!isScheduled) {
          await _scheduleNotificationForTime(
            day,
            time['hour'] as int,
            time['minute'] as int,
            title,
            message,
            details,
            notificationId,
          );
          box.write('notification_$notificationId', true);
        }
      }
    }
  }

// ==============================================================================
  // دالة حذف إشعار الطلب (تستدعى عند أخذ الطلب من سائق آخر)
  // ==============================================================================
  Future<void> cancelOrderNotification() async {
    // 1001 هو نفس الآيدي الذي استخدمناه عند عرض الإشعار
    await _flutterLocalNotificationsPlugin.cancel(id: 1001);
    print("🗑️ Order Notification Cancelled (Taken by another driver)");
  }

  Future<void> _scheduleNotificationForTime(
    int dayOffset,
    int hour,
    int minute,
    String title,
    String message,
    NotificationDetails details,
    int notificationId,
  ) async {
    tz.initializeTimeZones();
    var cairoLocation =
        tz.getLocation('Africa/Cairo'); // تأكد من المنطقة الزمنية

    final now = tz.TZDateTime.now(cairoLocation);
    tz.TZDateTime scheduledDate = tz.TZDateTime(
      cairoLocation,
      now.year,
      now.month,
      now.day + dayOffset,
      hour,
      minute,
    );

    if (scheduledDate.isBefore(now)) {
      scheduledDate = scheduledDate.add(const Duration(days: 1));
    }

    await _flutterLocalNotificationsPlugin.zonedSchedule(
      id: notificationId,
      title: title,
      body: message,
      scheduledDate: scheduledDate,
      notificationDetails: details,
      androidScheduleMode: AndroidScheduleMode.exact, // أو exactAllowWhileIdle
      matchDateTimeComponents: null,
    );
  }
}
