import 'package:kasy_kit/core/data/api/analytics_api.dart';
import 'package:kasy_kit/core/data/api/remote_config_api.dart';
import 'package:kasy_kit/core/data/api/tracking_api.dart';
import 'package:kasy_kit/core/dev_inspector/dev_inspector.dart';
import 'package:kasy_kit/core/initializer/onstart_widget.dart';
import 'package:kasy_kit/core/web_device_preview/web_device_preview.dart';
import 'package:kasy_kit/core/shared_preferences/shared_preferences.dart';
import 'package:kasy_kit/core/states/user_state_notifier.dart';
import 'package:kasy_kit/core/theme/colors.dart';
import 'package:kasy_kit/core/theme/extensions/theme_extension.dart';
import 'package:kasy_kit/core/theme/providers/theme_provider.dart';
import 'package:kasy_kit/core/theme/texts.dart';
import 'package:kasy_kit/core/theme/universal_theme.dart';
import 'package:kasy_kit/core/config/app_env.dart';
import 'package:kasy_kit/environnements.dart';
import 'package:kasy_kit/firebase_options_dev.dart' as firebase_dev;
import 'package:kasy_kit/i18n/translations.g.dart';
import 'package:kasy_kit/features/notifications/api/local_notifier.dart';
import 'package:kasy_kit/features/notifications/repositories/background_notification_handler.dart';
import 'package:kasy_kit/features/notifications/repositories/notifications_repository.dart';
import 'package:kasy_kit/features/subscription/repositories/subscription_repository.dart';
import 'package:kasy_kit/router.dart';
import 'package:device_preview/device_preview.dart';
import 'package:firebase_core/firebase_core.dart';
import 'package:firebase_messaging/firebase_messaging.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:flutter_localizations/flutter_localizations.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:logger/logger.dart';
import 'package:sentry_flutter/sentry_flutter.dart';
import 'package:shared_preferences/shared_preferences.dart';


void main() async {
  WidgetsFlutterBinding.ensureInitialized();
  await AppEnv.load();
  LocaleSettings.useDeviceLocale();
  final env = Environment.fromEnv();
  final logger = Logger();
  logger.i('Starting app in ${env.name} mode');
  // I like to force portrait mode on mobile devices
  // What is the last time you used an app in landscape mode?
  SystemChrome.setPreferredOrientations([
    DeviceOrientation.portraitUp,
    DeviceOrientation.portraitDown,
  ]);

  // initialize shared preferences for theme
  final sharedPrefs = await SharedPreferences.getInstance();

  // initialize firebase app for notifications
  await switch(env) {
    DevEnvironment() => Firebase.initializeApp(
      options: firebase_dev.DefaultFirebaseOptions.currentPlatform,
    ),
    ProdEnvironment() => Firebase.initializeApp(
      // Firebase is used here only for push notifications (FCM) and Remote Config.
      // If you use a single Firebase project for dev and prod (most common), this is correct.
      // If you have a separate Firebase project for production:
      //   1. Run: flutterfire configure --project=YOUR_PROD_PROJECT_ID --out=lib/firebase_options_prod.dart
      //   2. Import it: import 'package:kasy_kit/firebase_options_prod.dart' as firebase_prod;
      //   3. Replace the line below with: options: firebase_prod.DefaultFirebaseOptions.currentPlatform,
      options: firebase_dev.DefaultFirebaseOptions.currentPlatform,
    ),
  };

  

  // MUST be registered at the top-level BEFORE runApp().
  FirebaseMessaging.onBackgroundMessage(onBackgroundMessage);

  // initialize sentry for error reporting in production only
  if (env is DevEnvironment) {
    run(sharedPrefs);
  } else if (env is ProdEnvironment) {
    SentryFlutter.init((options) {
      options.dsn = env.sentryDsn;
      // 20% of traces will be sent to Sentry server. You should start with 1 and decrease it once you have more users.
      options.tracesSampleRate = 0.2;
      options.environment = env.name;
    }, appRunner: () => run(sharedPrefs));
  }
  
  
}

void run(SharedPreferences prefs) => runApp(
      TranslationProvider(
        child: ProviderScope(
          child: MyApp(
            sharedPreferences: prefs,
          ),
        ),
      ),
    );


// use this if you want to define different themes for different platforms
// notifier: AppTheme.adaptive(
//   defaultTextTheme: KasyTextTheme.build(),
//   ios: const IosThemeFactory(),
//   android: const AndroidThemeFactory(),
//   web: const WebThemeFactory(),
//   lightColors: KasyColors.light(),
//   darkColors: KasyColors.dark(),
//   mode: ThemeMode.dark,
// ),
// See ./docs/theme.md for more details
class MyApp extends ConsumerStatefulWidget {
  final SharedPreferences sharedPreferences;

  const MyApp({
    super.key,
    required this.sharedPreferences,
  });

  @override
  ConsumerState<MyApp> createState() => _MyAppState();
}

class _MyAppState extends ConsumerState<MyApp> {
  late final AppTheme _appTheme;

  @override
  void initState() {
    super.initState();
    _appTheme = AppTheme.uniform(
      sharedPreferences: widget.sharedPreferences,
      themeFactory: const UniversalThemeFactory(),
      lightColors: KasyColors.light(),
      darkColors: KasyColors.dark(),
      textTheme: KasyTextTheme.build(),
      defaultMode: ThemeMode.system,
    );
  }

  @override
  void dispose() {
    _appTheme.dispose();
    super.dispose();
  }

  // This widget is the root of your application.
  @override
  Widget build(BuildContext context) {
    ErrorWidget.builder = (FlutterErrorDetails details) {
      return AppErrorWidget(error: details);
    };
    final goRouter = ref.watch(goRouterProvider);

    return ThemeProvider(
      notifier: _appTheme,
      child: Builder(builder: (context) {
        return WebDevicePreview.wrap(
          child: DevInspector.wrap(
            child: MaterialApp.router(
              title: 'Kasy',
              scaffoldMessengerKey: devInspectorRootScaffoldMessengerKey,
              theme: ThemeProvider.of(context).light,
              darkTheme: ThemeProvider.of(context).dark,
              themeMode: ThemeProvider.of(context).mode,
              routerConfig: goRouter,
              localizationsDelegates: const [
                GlobalMaterialLocalizations.delegate,
                GlobalWidgetsLocalizations.delegate,
                GlobalCupertinoLocalizations.delegate,
              ],
              locale: TranslationProvider.of(context).flutterLocale,
              supportedLocales: AppLocaleUtils.supportedLocales,
              builder: (context, child) => Initializer(
                services: [
                  sharedPreferencesProvider,
                  remoteConfigApiProvider,
                  notificationsSettingsProvider,
                  notificationRepositoryProvider,
                  subscriptionRepositoryProvider,
                  userStateNotifierProvider.notifier,
                  analyticsApiProvider,
                  facebookEventApiProvider,
                ],
                onReady: DevicePreview.appBuilder(context, child),
                onError: (_, error) => InitializationErrorPage(error: error),
                onLoading: Scaffold(
                  body: Center(
                    child: CircularProgressIndicator.adaptive(
                      valueColor:
                          AlwaysStoppedAnimation<Color>(context.colors.primary),
                    ),
                  ),
                ),
              ),
            ),
          ),
        );
      }),
    );
  }
}

/// This is an example of a more user friendly error widget
/// By default Flutter will show a red screen with the error in debug mode
/// and a grey screen in release mode
class AppErrorWidget extends StatelessWidget {
  final FlutterErrorDetails? error;

  const AppErrorWidget({super.key, this.error});

  @override
  Widget build(BuildContext context) {
    return Container(
      padding: const EdgeInsets.all(16),
      color: Colors.orangeAccent,
      child: Column(
        mainAxisAlignment: MainAxisAlignment.center,
        children: [
          const Text(
            'Oups!',
            style: TextStyle(color: Colors.white, fontWeight: FontWeight.bold),
          ),
          const SizedBox(height: 8),
          const Text(
            'Sorry, Something went wrong',
            style: TextStyle(color: Colors.white),
          ),
          const SizedBox(height: 8),
          Text(
            '${error?.exception}\n',
            style: const TextStyle(color: Colors.white, fontSize: 10),
          ),
        ],
      ),
    );
  }
}

class InitializationErrorPage extends StatelessWidget {
  final String error;

  const InitializationErrorPage({super.key, required this.error});

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Padding(
        padding: const EdgeInsets.all(24.0),
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          crossAxisAlignment: CrossAxisAlignment.stretch,
          spacing: 8,
          children: [
            Text(
              'Cannot start app',
              style: context.textTheme.titleLarge,
            ),
            Text(
              'Check your internet connection and start again',
              style: context.textTheme.bodyLarge?.copyWith(
                color: context.colors.grey3,
              ),
            ),
            if (kDebugMode) 
              Text(
                "developper mode error: $error",
                style: context.textTheme.bodyLarge?.copyWith(
                  color: context.colors.error,
                ),
              ),
          ],
        ),
      ),
    );
  }
}