Implemented Loading Overlay

This commit is contained in:
2025-01-27 17:10:45 +01:00
parent 4765342ad1
commit 5df67920ea
2 changed files with 84 additions and 2 deletions

View File

@@ -3,6 +3,7 @@ import 'package:provider/provider.dart';
import '../widgets/flood_station_list_view.dart';
import '../services/flood_station_provider.dart';
import '../widgets/loading_notifier.dart';
import '../widgets/station_filter.dart';
import 'flood_station_page.dart';
@@ -17,11 +18,19 @@ class LandingPage extends StatefulWidget {
class _LandingPageState extends State<LandingPage> {
late FloodStationProvider floodStationProvider;
bool _isLoading = false;
OverlayEntry? _overlayEntry;
@override
initState() {
super.initState();
WidgetsBinding.instance
.addPostFrameCallback((_) => floodStationProvider.loadAllStations());
WidgetsBinding.instance.addPostFrameCallback((_) {
_isLoading = true;
showLoadingNotifier(context: context, message: 'Loading');
floodStationProvider
.loadAllStations()
.whenComplete(() => removeLoadingNotifier());
});
}
@override
@@ -46,4 +55,35 @@ class _LandingPageState extends State<LandingPage> {
),
);
}
Future<void> showLoadingNotifier({
required BuildContext context,
required String message,
}) async {
OverlayState? overlayState = Overlay.of(context);
_overlayEntry = OverlayEntry(
builder: (c) {
return Positioned(
bottom: 16,
left: 0,
right: 0,
child: Center(
child: LoadingNotifier(
message: 'Loading',
onDismissed: () => removeLoadingNotifier(),
),
),
);
},
);
overlayState.insert(_overlayEntry!);
overlayState.setState(() {});
}
void removeLoadingNotifier() {
if (_overlayEntry != null) {
_overlayEntry?.remove();
_overlayEntry = null;
}
}
}

View File

@@ -0,0 +1,42 @@
import 'package:flutter/material.dart';
class LoadingNotifier extends StatelessWidget {
const LoadingNotifier(
{super.key, required this.onDismissed, required this.message});
final void Function() onDismissed;
final String message;
@override
Widget build(BuildContext context) {
return Card(
color: Theme.of(context).colorScheme.primaryContainer,
shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(45)),
child: SizedBox(
width: 500,
height: 60,
child: Padding(
padding: const EdgeInsets.symmetric(horizontal: 20),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
mainAxisSize: MainAxisSize.max,
children: [
SizedBox(
width: 25,
height: 25,
child: CircularProgressIndicator(),
),
Text(
message,
style: Theme.of(context).textTheme.titleSmall,
),
IconButton(
onPressed: () => onDismissed(),
icon: Icon(Icons.close),
)
],
),
),
),
);
}
}