import 'package:fl_clash/common/common.dart'; import 'package:fl_clash/core/core.dart'; import 'package:fl_clash/enum/enum.dart'; import 'package:fl_clash/models/models.dart'; import 'package:fl_clash/providers/app.dart'; import 'package:fl_clash/providers/config.dart'; import 'package:fl_clash/providers/state.dart'; import 'package:fl_clash/state.dart'; import 'package:flutter/material.dart'; import 'package:flutter_riverpod/flutter_riverpod.dart'; class CoreManager extends ConsumerStatefulWidget { final Widget child; const CoreManager({super.key, required this.child}); @override ConsumerState createState() => _CoreContainerState(); } class _CoreContainerState extends ConsumerState with CoreEventListener { @override Widget build(BuildContext context) { return widget.child; } @override void initState() { super.initState(); coreEventManager.addListener(this); ref.listenManual(needSetupProvider, (prev, next) { if (prev != next) { globalState.appController.handleChangeProfile(); } }); ref.listenManual(updateParamsProvider, (prev, next) { if (prev != next) { globalState.appController.updateClashConfigDebounce(); } }); ref.listenManual(appSettingProvider.select((state) => state.openLogs), ( prev, next, ) { if (next) { coreController.startLog(); } else { coreController.stopLog(); } }, fireImmediately: true); } @override Future dispose() async { coreEventManager.removeListener(this); super.dispose(); } @override Future onDelay(Delay delay) async { super.onDelay(delay); final appController = globalState.appController; appController.setDelay(delay); debouncer.call(FunctionTag.updateDelay, () async { appController.updateGroupsDebounce(); }, duration: const Duration(milliseconds: 5000)); } @override void onLog(Log log) { ref.read(logsProvider.notifier).addLog(log); if (log.logLevel == LogLevel.error) { globalState.showNotifier(log.payload); } super.onLog(log); } @override void onRequest(TrackerInfo trackerInfo) async { ref.read(requestsProvider.notifier).addRequest(trackerInfo); super.onRequest(trackerInfo); } @override Future onLoaded(String providerName) async { ref .read(providersProvider.notifier) .setProvider(await coreController.getExternalProvider(providerName)); debouncer.call(FunctionTag.loadedProvider, () async { globalState.appController.updateGroupsDebounce(); }, duration: const Duration(milliseconds: 5000)); super.onLoaded(providerName); } @override Future onCrash(String message) async { if (!globalState.isUserDisconnected && WidgetsBinding.instance.lifecycleState == AppLifecycleState.resumed) { context.showNotifier(message); } globalState.isUserDisconnected = false; if (ref.read(coreStatusProvider) != CoreStatus.connected) { return; } ref.read(coreStatusProvider.notifier).value = CoreStatus.disconnected; await coreController.shutdown(); super.onCrash(message); } }