2021-04-15 11:34:49 +00:00
import ' package:comunic/helpers/firebase_messaging_helper.dart ' ;
2021-04-13 15:56:55 +00:00
import ' package:comunic/helpers/independent_push_notifications_helper.dart ' ;
2021-04-12 17:26:05 +00:00
import ' package:comunic/helpers/push_notifications_helper.dart ' ;
import ' package:comunic/helpers/server_config_helper.dart ' ;
import ' package:comunic/models/config.dart ' ;
import ' package:comunic/ui/widgets/async_screen_widget.dart ' ;
import ' package:comunic/utils/flutter_utils.dart ' ;
import ' package:comunic/utils/intl_utils.dart ' ;
import ' package:comunic/utils/log_utils.dart ' ;
import ' package:comunic/utils/ui_utils.dart ' ;
import ' package:flutter/material.dart ' ;
/// Push notifications configuration route
///
/// @author Pierre Hubert
Future < void > showInitialPushNotificationsConfiguration (
BuildContext context ) async {
// Check if no notifications service are available
2021-04-13 15:56:55 +00:00
if ( ! PushNotificationsHelper . arePushNotificationsAvailable ) return ;
2021-04-12 17:26:05 +00:00
await Navigator . of ( context ) . push (
MaterialPageRoute ( builder: ( c ) = > PushNotificationsConfigurationRoute ( ) ) ) ;
}
class PushNotificationsConfigurationRoute extends StatefulWidget {
@ override
_PushNotificationsConfigurationRouteState createState ( ) = >
_PushNotificationsConfigurationRouteState ( ) ;
}
class _PushNotificationsConfigurationRouteState
extends State < PushNotificationsConfigurationRoute > {
PushNotificationsStatus currStatus ;
bool get canSubmit = >
( currStatus ? ? PushNotificationsStatus . UNDEFINED ) ! =
PushNotificationsStatus . UNDEFINED ;
Future < void > _refresh ( ) async {
await PushNotificationsHelper . refreshLocalStatus ( ) ;
currStatus = await PushNotificationsHelper . getLocalStatus ( ) ;
}
@ override
Widget build ( BuildContext context ) {
return Material (
2021-04-13 17:06:31 +00:00
textStyle: TextStyle ( color: Colors . white ) ,
2021-04-12 17:26:05 +00:00
color: config ( ) . splashBackgroundColor ,
child: Center (
child: Padding (
padding: const EdgeInsets . all ( 8.0 ) ,
child: AsyncScreenWidget (
onReload: _refresh ,
onBuild: _buildForm ,
errorMessage: tr ( " Failed to load push notifications settings! " ) ,
) ,
) ,
) ) ;
}
Widget _buildForm ( ) = > ConstrainedBox (
constraints: BoxConstraints ( maxWidth: 300 ) ,
child: Column (
mainAxisAlignment: MainAxisAlignment . center ,
children: [
Spacer ( ) ,
2021-04-13 17:06:31 +00:00
Icon ( Icons . notifications_none , color: Colors . white ) ,
2021-04-12 17:26:05 +00:00
Spacer ( ) ,
Text (
tr ( " Comunic can now send you notifications to your device when the application is closed if you want. " ) ,
textAlign: TextAlign . center ,
) ,
Spacer ( ) ,
_NotificationOption (
title: tr ( " Use Google services " ) ,
description: tr (
" Use the Google Play services to send you notifications. This option is less privacy-friendly, but it will work on most phones and will save your battery life. " ) ,
option: PushNotificationsStatus . FIREBASE ,
current: currStatus ,
available: srvConfig . notificationsPolicy . hasFirebase ,
onChanged: ( s ) = > setState ( ( ) = > currStatus = s ) ,
) ,
_NotificationOption (
title: tr ( " Use independent notifications service " ) ,
description: tr (
" Configure Comunic to use your own self-hosted notifications service. This option is much more privacy-friendly, but it will drain your battery life. " ) ,
option: PushNotificationsStatus . INDEPENDENT ,
current: currStatus ,
available:
srvConfig . notificationsPolicy . hasIndependent & & isAndroid ,
onChanged: ( s ) = > setState ( ( ) = > currStatus = s ) ,
) ,
_NotificationOption (
title: tr ( " Do not send notification " ) ,
description: tr (
" Disable notifications services. You will always be able to change it from application settings. " ) ,
option: PushNotificationsStatus . DISABLED ,
current: currStatus ,
available: true ,
onChanged: ( s ) = > setState ( ( ) = > currStatus = s ) ,
) ,
Spacer ( ) ,
OutlinedButton (
onPressed: canSubmit ? _submit : null ,
child: Text ( tr ( " Configure " ) . toUpperCase ( ) ) ,
style: OutlinedButton . styleFrom ( primary: Colors . white ) ) ,
Spacer ( ) ,
] ,
) ,
) ;
Future < void > _submit ( ) async {
try {
2021-04-15 11:34:49 +00:00
String firebaseToken = " " ;
2021-04-16 06:22:05 +00:00
if ( currStatus = = await PushNotificationsHelper . getLocalStatus ( ) ) {
Navigator . of ( context ) . pop ( ) ;
return ;
}
2021-04-12 17:26:05 +00:00
switch ( currStatus ) {
case PushNotificationsStatus . DISABLED:
break ;
case PushNotificationsStatus . FIREBASE:
2021-04-15 11:34:49 +00:00
await FirebaseMessagingHelper . preConfigure ( ) ;
firebaseToken = await FirebaseMessagingHelper . getToken ( ) ;
2021-04-12 17:26:05 +00:00
break ;
2021-04-13 15:56:55 +00:00
2021-04-12 17:26:05 +00:00
case PushNotificationsStatus . INDEPENDENT:
2021-04-13 17:45:18 +00:00
if ( await IndependentPushNotificationsHelper . needPreConfiguration ( ) )
await IndependentPushNotificationsHelper . preConfigure ( context ) ;
2021-04-12 17:26:05 +00:00
break ;
default :
throw new Exception ( " Unknown status! " ) ;
}
await PushNotificationsHelper . clearLocalStatus ( ) ;
2021-04-15 11:34:49 +00:00
await PushNotificationsHelper . setNewStatus ( currStatus ,
firebaseToken: firebaseToken ) ;
2021-04-12 17:26:05 +00:00
await PushNotificationsHelper . refreshLocalStatus ( ) ;
Navigator . of ( context ) . pop ( ) ;
} catch ( e , s ) {
logError ( e , s ) ;
showAlert (
context: context ,
message: tr ( " Failed to configure push notifications! " ) ) ;
}
}
}
class _NotificationOption extends StatelessWidget {
final String title ;
final String description ;
final PushNotificationsStatus option ;
final PushNotificationsStatus current ;
final bool available ;
final Function ( PushNotificationsStatus ) onChanged ;
const _NotificationOption ( {
Key key ,
@ required this . title ,
@ required this . description ,
@ required this . option ,
@ required this . current ,
@ required this . available ,
@ required this . onChanged ,
} ) : assert ( title ! = null ) ,
assert ( description ! = null ) ,
assert ( option ! = null ) ,
assert ( current ! = null ) ,
assert ( available ! = null ) ,
assert ( onChanged ! = null ) ,
super ( key: key ) ;
@ override
Widget build ( BuildContext context ) = > ! available
? Container ( )
: Theme (
data: Theme . of ( context ) . copyWith (
2021-04-13 17:06:31 +00:00
splashColor: Colors . transparent ,
highlightColor: Colors . transparent ) ,
2021-04-12 17:26:05 +00:00
child: ListTile (
leading: Radio (
value: option ,
groupValue: current ,
onChanged: onChanged ,
2021-04-13 17:06:31 +00:00
fillColor: MaterialStateProperty . all ( Colors . white ) ,
2021-04-12 17:26:05 +00:00
) ,
2021-04-13 17:06:31 +00:00
title: Text ( title , style: TextStyle ( color: Colors . white ) ) ,
subtitle: Text ( description , style: TextStyle ( color: Colors . white ) ) ,
2021-04-12 17:26:05 +00:00
contentPadding: EdgeInsets . all ( 0 ) ,
onTap: ( ) = > onChanged ( option ) ,
) ,
) ;
}