Skip to content

Instantly share code, notes, and snippets.

@niwatly
Last active March 19, 2023 09:33
Show Gist options
  • Save niwatly/2314cc296f14a2b3f07950cc81a839d8 to your computer and use it in GitHub Desktop.
Save niwatly/2314cc296f14a2b3f07950cc81a839d8 to your computer and use it in GitHub Desktop.
アプリのforeground状態を通知してくれるStream example
import 'package:collabo_base_app/common.dart';
import 'package:flutter/widgets.dart';
import 'package:is_lock_screen/is_lock_screen.dart';
import 'package:rxdart/rxdart.dart';
class AppStateNotifier with WidgetsBindingObserver {
final Subject<AppLifecycleState> _appStateChanged = PublishSubject();
late Stream<AppLifecycleState> appStateStream;
final CompositeSubscription _compositeSubscription = CompositeSubscription();
AppStateNotifier() {
WidgetsBinding.instance.addObserver(this);
appStateStream = _appStateChanged.stream //
.publishValue()
..connect().addTo(_compositeSubscription);
_sendInitialAppState();
}
Future _sendInitialAppState() async {
// 背景: hot restart とすると アプリがバックグラウンド状態でもアプリ起動処理が走る
// 背景: アプリがバックグラウンド状態だと、Providerによる状態変化の通知が発生しない(Widgetをbuildする必要ないもん当たり前?)
// 背景: Providerによる状態変化の通知が発生しないとAPIリクエストに認証情報を付与できない
// 問題: アプリがバックグラウンド状態のときにhot restart するとログイン画面に飛ばされる(大抵の場合利用規約への同意状態取得APIが401)
// FIXME: 「アプリがバックグラウンド状態の間はAPIリクエストをしない」ように書きたかったんだけど、アプリの現状態を知るすべがなくて困ってる。didChangeAppLifecycleState は状態が変化したときしか通知してくれない
// FIXME: OSのホーム画面にいるときのユースケースに対応できていない
var v = AppLifecycleState.resumed;
try {
final res = await isLockScreen();
if (res == true) {
v = AppLifecycleState.inactive;
}
} catch (e, st) {
recordError(e, st);
} finally {
_appStateChanged.add(v);
}
}
void dispose() {
WidgetsBinding.instance.removeObserver(this);
_compositeSubscription.dispose();
}
@override
void didChangeAppLifecycleState(AppLifecycleState state) {
_appStateChanged.add(state);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment