mirror of
https://github.com/krille-chan/fluffychat
synced 2024-09-10 09:45:14 +00:00
feat: Background fetch mode on Android
This adds a background fetch mode on android which makes sure that the flutter engine is not rendered when the app started to process background push notifications only. This should safe some resources like battery and performance and should make processing background notifications faster.
This commit is contained in:
parent
3b12d8ab84
commit
c7c801c695
1 changed files with 53 additions and 2 deletions
|
@ -5,6 +5,7 @@ import 'package:flutter_app_lock/flutter_app_lock.dart';
|
|||
import 'package:flutter_secure_storage/flutter_secure_storage.dart';
|
||||
import 'package:matrix/matrix.dart';
|
||||
|
||||
import 'package:fluffychat/config/app_config.dart';
|
||||
import 'package:fluffychat/utils/client_manager.dart';
|
||||
import 'package:fluffychat/utils/platform_infos.dart';
|
||||
import 'config/setting_keys.dart';
|
||||
|
@ -13,7 +14,7 @@ import 'widgets/fluffy_chat_app.dart';
|
|||
import 'widgets/lock_screen.dart';
|
||||
|
||||
void main() async {
|
||||
Logs().i('Welcome to FluffyChat');
|
||||
Logs().i('Welcome to ${AppConfig.applicationName} <3');
|
||||
|
||||
// Our background push shared isolate accesses flutter-internal things very early in the startup proccess
|
||||
// To make sure that the parts of flutter needed are started up already, we need to ensure that the
|
||||
|
@ -28,9 +29,34 @@ void main() async {
|
|||
await firstClient?.roomsLoading;
|
||||
await firstClient?.accountDataLoading;
|
||||
|
||||
// If the app starts in detached mode, we assume that it is in
|
||||
// background fetch mode for processing push notifications. This is
|
||||
// currently only supported on Android.
|
||||
if (PlatformInfos.isAndroid &&
|
||||
AppLifecycleState.detached == WidgetsBinding.instance.lifecycleState) {
|
||||
// In the background fetch mode we do not want to waste ressources with
|
||||
// starting the Flutter engine but process incoming push notifications.
|
||||
BackgroundPush.clientOnly(clients.first);
|
||||
// To start the flutter engine afterwards we add an custom observer.
|
||||
WidgetsBinding.instance.addObserver(AppStarter(clients));
|
||||
Logs().i(
|
||||
'${AppConfig.applicationName} started in background-fetch mode. No GUI will be created unless the app is no longer detached.',
|
||||
);
|
||||
return;
|
||||
}
|
||||
|
||||
// Started in foreground mode.
|
||||
Logs().i(
|
||||
'${AppConfig.applicationName} started in foreground mode. Rendering GUI...',
|
||||
);
|
||||
await startGui(clients);
|
||||
}
|
||||
|
||||
/// Fetch the pincode for the applock and start the flutter engine.
|
||||
Future<void> startGui(List<Client> clients) async {
|
||||
// Fetch the pin for the applock if existing for mobile applications.
|
||||
String? pin;
|
||||
if (PlatformInfos.isMobile) {
|
||||
BackgroundPush.clientOnly(clients.first);
|
||||
try {
|
||||
pin =
|
||||
await const FlutterSecureStorage().read(key: SettingKeys.appLockKey);
|
||||
|
@ -39,6 +65,9 @@ void main() async {
|
|||
}
|
||||
}
|
||||
|
||||
// Start rendering the Flutter app and wrap it in an Applock.
|
||||
// We do this only for mobile applications as we saw routing
|
||||
// problems on other platforms if we wrap it always.
|
||||
runApp(
|
||||
PlatformInfos.isMobile
|
||||
? AppLock(
|
||||
|
@ -49,3 +78,25 @@ void main() async {
|
|||
: FluffyChatApp(clients: clients),
|
||||
);
|
||||
}
|
||||
|
||||
/// Watches the lifecycle changes to start the application when it
|
||||
/// is no longer detached.
|
||||
class AppStarter with WidgetsBindingObserver {
|
||||
final List<Client> clients;
|
||||
bool guiStarted = false;
|
||||
|
||||
AppStarter(this.clients);
|
||||
|
||||
@override
|
||||
void didChangeAppLifecycleState(AppLifecycleState state) {
|
||||
if (guiStarted) return;
|
||||
if (state == AppLifecycleState.detached) return;
|
||||
|
||||
Logs().i(
|
||||
'${AppConfig.applicationName} switches from the detached background-fetch mode to ${state.name} mode. Rendering GUI...',
|
||||
);
|
||||
startGui(clients);
|
||||
// We must make sure that the GUI is only started once.
|
||||
guiStarted = true;
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue