together_mobile/lib/use_notification.dart

270 lines
8.2 KiB
Dart

import 'dart:io';
import 'package:flutter/cupertino.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:flutter_timezone/flutter_timezone.dart';
import 'package:flutter_local_notifications/flutter_local_notifications.dart';
import 'package:timezone/timezone.dart' as tz;
import 'package:timezone/data/latest_all.dart' as tz;
import 'package:together_mobile/notification_api.dart';
Future<void> main() async {
// needed if you intend to initialize in `main` function
WidgetsFlutterBinding.ensureInitialized();
final NotificationAppLaunchDetails? notificationAppLaunchDetails = !kIsWeb &&
Platform.isLinux
? null
: await flutterLocalNotificationsPlugin.getNotificationAppLaunchDetails();
const AndroidInitializationSettings initializationSettingsAndroid =
AndroidInitializationSettings('app_icon');
final List<DarwinNotificationCategory> darwinNotificationCategories = [
DarwinNotificationCategory(
darwinNotificationCategoryText,
actions: [
DarwinNotificationAction.text(
'text_1',
'Action 1',
buttonTitle: 'Send',
placeholder: 'Placeholder',
),
],
),
DarwinNotificationCategory(
darwinNotificationCategoryPlain,
actions: <DarwinNotificationAction>[
DarwinNotificationAction.plain('id_1', 'Action 1'),
DarwinNotificationAction.plain(
'id_2',
'Action 2 (destructive)',
options: <DarwinNotificationActionOption>{
DarwinNotificationActionOption.destructive,
},
),
DarwinNotificationAction.plain(
navigationActionId,
'Action 3 (foreground)',
options: <DarwinNotificationActionOption>{
DarwinNotificationActionOption.foreground,
},
),
DarwinNotificationAction.plain(
'id_4',
'Action 4 (auth required)',
options: <DarwinNotificationActionOption>{
DarwinNotificationActionOption.authenticationRequired,
},
),
],
options: <DarwinNotificationCategoryOption>{
DarwinNotificationCategoryOption.hiddenPreviewShowTitle,
},
),
];
final DarwinInitializationSettings initializationSettingsDarwin =
DarwinInitializationSettings(
requestAlertPermission: false,
requestBadgePermission: false,
requestSoundPermission: false,
onDidReceiveLocalNotification: (id, title, body, payload) async {
didReceiveLocalNotificationStream.add(
ReceivedNotification(
id: id,
title: title,
body: body,
payload: payload,
),
);
},
notificationCategories: darwinNotificationCategories,
);
final LinuxInitializationSettings initializationSettingsLinux =
LinuxInitializationSettings(
defaultActionName: 'Open notification',
defaultIcon: AssetsLinuxIcon('icons/app_icon.png'),
);
final InitializationSettings initializationSettings = InitializationSettings(
android: initializationSettingsAndroid,
iOS: initializationSettingsDarwin,
macOS: initializationSettingsDarwin,
linux: initializationSettingsLinux,
);
await flutterLocalNotificationsPlugin.initialize(
initializationSettings,
onDidReceiveNotificationResponse:
(NotificationResponse notificationResponse) {
switch (notificationResponse.notificationResponseType) {
case NotificationResponseType.selectedNotification:
selectNotificationStream.add(notificationResponse.payload);
break;
case NotificationResponseType.selectedNotificationAction:
if (notificationResponse.actionId == navigationActionId) {
selectNotificationStream.add(notificationResponse.payload);
}
break;
}
},
onDidReceiveBackgroundNotificationResponse: notificationTapBackground,
);
String initialRoute = HomePage.routeName;
runApp(
MaterialApp(
initialRoute: initialRoute,
routes: <String, WidgetBuilder>{
HomePage.routeName: (_) => HomePage(notificationAppLaunchDetails),
SecondPage.routeName: (_) => SecondPage(selectedNotificationPayload),
},
),
);
}
Future<void> _configureLocalTimeZone() async {
if (kIsWeb || Platform.isLinux) {
return;
}
tz.initializeTimeZones();
final String timeZoneName = await FlutterTimezone.getLocalTimezone();
tz.setLocalLocation(tz.getLocation(timeZoneName));
}
class PaddedElevatedButton extends StatelessWidget {
const PaddedElevatedButton({
required this.buttonText,
required this.onPressed,
Key? key,
}) : super(key: key);
final String buttonText;
final VoidCallback onPressed;
@override
Widget build(BuildContext context) => Padding(
padding: const EdgeInsets.fromLTRB(0, 0, 0, 8),
child: ElevatedButton(
onPressed: onPressed,
child: Text(buttonText),
),
);
}
class HomePage extends StatefulWidget {
const HomePage(this.notificationAppLaunchDetails, {Key? key})
: super(key: key);
static String routeName = '/';
final NotificationAppLaunchDetails? notificationAppLaunchDetails;
bool get didNotificationLaunchApp =>
notificationAppLaunchDetails?.didNotificationLaunchApp ?? false;
@override
State<HomePage> createState() => _HomePageState();
}
class _HomePageState extends State<HomePage> {
bool _notificationsEnabled = false;
@override
void initState() {
super.initState();
_isAndroidPermissionGranted();
_requestPermissions();
_configureDidReceivelocalNotificationSubject();
_configureSelectNotificationSubject();
}
Future<void> _isAndroidPermissionGranted() async {
if (Platform.isAndroid) {
final bool granted = await flutterLocalNotificationsPlugin
.resolvePlatformSpecificImplementation<
AndroidFlutterLocalNotificationsPlugin>()
?.areNotificationsEnabled() ??
false;
setState(() {
_notificationsEnabled = granted;
});
}
}
Future<void> _requestPermissions() async {
if (Platform.isIOS || Platform.isMacOS) {
await flutterLocalNotificationsPlugin
.resolvePlatformSpecificImplementation<
IOSFlutterLocalNotificationsPlugin>()
?.requestPermissions(
alert: true,
badge: true,
sound: true,
);
await flutterLocalNotificationsPlugin
.resolvePlatformSpecificImplementation<
MacOSFlutterLocalNotificationsPlugin>()
?.requestPermissions(
alert: true,
badge: true,
sound: true,
);
} else if (Platform.isAndroid) {
final AndroidFlutterLocalNotificationsPlugin? androidImplementation =
flutterLocalNotificationsPlugin.resolvePlatformSpecificImplementation<
AndroidFlutterLocalNotificationsPlugin>();
final bool? granted = await androidImplementation?.requestPermission();
setState(() {
_notificationsEnabled = granted ?? false;
});
}
}
void _configureDidReceiveLocalNotificationSubject() {
didReceiveLocalNotificationStream.stream
.listen((ReceivedNotification receivedNotification) async {
await showDialog(
context: context,
builder: (BuildContext context) => CupertinoAlertDialog(
title: receivedNotification.title != null
? Text(receivedNotification.title!)
: null,
content: receivedNotification.body != null
? Text(receivedNotification.body!)
: null,
actions: <Widget>[
CupertinoDialogAction(
isDefaultAction: true,
onPressed: () async {
Navigator.of(context, rootNavigator: true).pop();
await Navigator.of(context).push(
MaterialPageRoute<void>(
builder: (BuildContext context) =>
SecondPage(receivedNotification.payload),
),
);
},
child: const Text('Ok'),
)
],
),
);
});
}
@override
Widget build(BuildContext context) {
return const Placeholder();
}
}