// ignore_for_file: use_build_context_synchronously import 'dart:io'; import 'package:flutter/material.dart'; import 'package:animations/animations.dart'; import 'package:flutter/rendering.dart'; import 'package:flutter_split_view/flutter_split_view.dart'; import 'package:provider/provider.dart'; import 'package:flutter_gen/gen_l10n/app_localizations.dart'; import 'package:adguard_home_manager/screens/clients/client/client_screen_functions.dart'; import 'package:adguard_home_manager/screens/clients/client/added_client_tile.dart'; import 'package:adguard_home_manager/screens/clients/client/remove_client_modal.dart'; import 'package:adguard_home_manager/screens/clients/fab.dart'; import 'package:adguard_home_manager/screens/clients/options_modal.dart'; import 'package:adguard_home_manager/widgets/tab_content_list.dart'; import 'package:adguard_home_manager/functions/snackbar.dart'; import 'package:adguard_home_manager/providers/status_provider.dart'; import 'package:adguard_home_manager/providers/clients_provider.dart'; import 'package:adguard_home_manager/constants/enums.dart'; import 'package:adguard_home_manager/classes/process_modal.dart'; import 'package:adguard_home_manager/models/clients.dart'; import 'package:adguard_home_manager/providers/app_config_provider.dart'; class AddedList extends StatefulWidget { final ScrollController scrollController; final List data; final void Function(Client) onClientSelected; final Client? selectedClient; final bool splitView; const AddedList({ Key? key, required this.scrollController, required this.data, required this.onClientSelected, this.selectedClient, required this.splitView }) : super(key: key); @override State createState() => _AddedListState(); } class _AddedListState extends State { late bool isVisible; @override initState(){ super.initState(); isVisible = true; widget.scrollController.addListener(() { if (widget.scrollController.position.userScrollDirection == ScrollDirection.reverse) { if (mounted && isVisible == true) { setState(() => isVisible = false); } } else { if (widget.scrollController.position.userScrollDirection == ScrollDirection.forward) { if (mounted && isVisible == false) { setState(() => isVisible = true); } } } }); } @override Widget build(BuildContext context) { final statusProvider = Provider.of(context); final clientsProvider = Provider.of(context); final appConfigProvider = Provider.of(context); final width = MediaQuery.of(context).size.width; void confirmEditClient(Client client) async { ProcessModal processModal = ProcessModal(context: context); processModal.open(AppLocalizations.of(context)!.addingClient); final result = await clientsProvider.editClient(client); processModal.close(); if (result == true) { showSnacbkar( appConfigProvider: appConfigProvider, label: AppLocalizations.of(context)!.clientUpdatedSuccessfully, color: Colors.green ); } else { showSnacbkar( appConfigProvider: appConfigProvider, label: AppLocalizations.of(context)!.clientNotUpdated, color: Colors.red ); } } void deleteClient(Client client) async { ProcessModal processModal = ProcessModal(context: context); processModal.open(AppLocalizations.of(context)!.removingClient); final result = await clientsProvider.deleteClient(client); processModal.close(); if (result == true) { if (widget.splitView == true) { SplitView.of(context).popUntil(0); } showSnacbkar( appConfigProvider: appConfigProvider, label: AppLocalizations.of(context)!.clientDeletedSuccessfully, color: Colors.green ); } else { showSnacbkar( appConfigProvider: appConfigProvider, label: AppLocalizations.of(context)!.clientNotDeleted, color: Colors.red ); } } void openClientModal(Client client) { openClientFormModal( context: context, width: width, onConfirm: confirmEditClient, onDelete: deleteClient ); } void openDeleteModal(Client client) { showModal( context: context, builder: (ctx) => RemoveClientModal( onConfirm: () => deleteClient(client) ) ); } void openOptionsModal(Client client) { showModal( context: context, builder: (ctx) => OptionsModal( onDelete: () => openDeleteModal(client), onEdit: () => openClientModal(client), ) ); } return CustomTabContentList( noSliver: !(Platform.isAndroid || Platform.isIOS), listPadding: widget.splitView == true ? const EdgeInsets.only(top: 8) : null, loadingGenerator: () => SizedBox( width: double.maxFinite, child: Column( mainAxisAlignment: MainAxisAlignment.center, crossAxisAlignment: CrossAxisAlignment.center, children: [ const CircularProgressIndicator(), const SizedBox(height: 30), Text( AppLocalizations.of(context)!.loadingStatus, textAlign: TextAlign.center, style: TextStyle( fontSize: 22, color: Theme.of(context).colorScheme.onSurfaceVariant, ), ) ], ), ), itemsCount: widget.data.length, contentWidget: (index) => AddedClientTile( selectedClient: widget.selectedClient, client: widget.data[index], onTap: widget.onClientSelected, onLongPress: openOptionsModal, onEdit: statusProvider.serverStatus != null ? (c) => openClientModal(c) : null, onDelete: openDeleteModal, splitView: widget.splitView, serverVersion: statusProvider.serverStatus!.serverVersion, ), noData: SizedBox( width: double.maxFinite, child: Column( mainAxisAlignment: MainAxisAlignment.center, children: [ Padding( padding: const EdgeInsets.symmetric(horizontal: 16), child: Text( AppLocalizations.of(context)!.noClientsList, textAlign: TextAlign.center, style: TextStyle( fontSize: 24, color: Theme.of(context).colorScheme.onSurfaceVariant, ), ), ), const SizedBox(height: 30), TextButton.icon( onPressed: () => clientsProvider.fetchClients(updateLoading: true), icon: const Icon(Icons.refresh_rounded), label: Text(AppLocalizations.of(context)!.refresh), ) ], ), ), errorGenerator: () => SizedBox( width: double.maxFinite, child: Column( mainAxisAlignment: MainAxisAlignment.center, crossAxisAlignment: CrossAxisAlignment.center, children: [ const Icon( Icons.error, color: Colors.red, size: 50, ), const SizedBox(height: 30), Text( AppLocalizations.of(context)!.errorLoadServerStatus, textAlign: TextAlign.center, style: TextStyle( fontSize: 22, color: Theme.of(context).colorScheme.onSurfaceVariant, ), ) ], ), ), loadStatus: statusProvider.loadStatus == LoadStatus.loading || clientsProvider.loadStatus == LoadStatus.loading ? LoadStatus.loading : clientsProvider.loadStatus, onRefresh: () => clientsProvider.fetchClients(updateLoading: false), fab: const ClientsFab(), fabVisible: isVisible, ); } }